diff --git a/AlgebraicDataflowArchitectureModel/src/algorithms/FinalDecisionOfStoringResourceStates.java b/AlgebraicDataflowArchitectureModel/src/algorithms/FinalDecisionOfStoringResourceStates.java index 715fdd2..b466fd7 100644 --- a/AlgebraicDataflowArchitectureModel/src/algorithms/FinalDecisionOfStoringResourceStates.java +++ b/AlgebraicDataflowArchitectureModel/src/algorithms/FinalDecisionOfStoringResourceStates.java @@ -31,34 +31,6 @@ flag = false; } } -// if (resource.getInEdges().size() == 0) -// flag = true; ((StoreAttribute) resource.getAttribute()).setStored(flag); - if (resource.getIdentifierTemplate().getResourceStateType() == null) { - for (Edge e : resource.getInEdges()) { - for (ChannelMember cm : ((ResourceDependency) e).getChannelGenerator().getChannelMembers()) { - if (((PushPullAttribute) ((ResourceDependency) e).getAttribute()).getOptions().get(0) == PushPullValue.PUSH - && cm.getStateTransition().getNextStateExpression().getClass() == Term.class) { - if (((Term) cm.getStateTransition().getNextStateExpression()).getSymbol().getName().equals("cons")) { - resource.getIdentifierTemplate().setResourceStateType(DataConstraintModel.typeList); - } - } - break; - } - } - for (Edge e : resource.getOutEdges()) { - for (ChannelMember cm : ((ResourceDependency) e).getChannelGenerator().getChannelMembers()) { - if (((PushPullAttribute) ((ResourceDependency) e).getAttribute()).getOptions().get(0) != PushPullValue.PUSH - && cm.getStateTransition().getNextStateExpression().getClass() == Term.class) { - if (((Term) cm.getStateTransition().getNextStateExpression()).getSymbol().getName().equals("cons")) { - resource.getIdentifierTemplate().setResourceStateType(DataConstraintModel.typeList); - } - } - break; - } - } - if (resource.getIdentifierTemplate().getResourceStateType() == null) - resource.getIdentifierTemplate().setResourceStateType(DataConstraintModel.typeInt); - } } } diff --git a/AlgebraicDataflowArchitectureModel/src/algorithms/JavaCodeGenerator.java b/AlgebraicDataflowArchitectureModel/src/algorithms/JavaCodeGenerator.java index 878c8e2..93f04d5 100644 --- a/AlgebraicDataflowArchitectureModel/src/algorithms/JavaCodeGenerator.java +++ b/AlgebraicDataflowArchitectureModel/src/algorithms/JavaCodeGenerator.java @@ -244,7 +244,7 @@ if (type.getTypeName() != mainTypeName) { String cons = "\t" + "private " + field.getType().getInterfaceTypeName() + " " + field.getName(); - if (field.getType().equals(DataConstraintModel.typeList)) + if (DataConstraintModel.isListType(field.getType())) cons += " = new ArrayList<>()"; cons += ";"; codes.add(cons); diff --git a/AlgebraicDataflowArchitectureModel/src/algorithms/JerseyCodeGenerator.java b/AlgebraicDataflowArchitectureModel/src/algorithms/JerseyCodeGenerator.java index 9fad21e..8b35a6a 100644 --- a/AlgebraicDataflowArchitectureModel/src/algorithms/JerseyCodeGenerator.java +++ b/AlgebraicDataflowArchitectureModel/src/algorithms/JerseyCodeGenerator.java @@ -172,7 +172,7 @@ if (type.getTypeName() != mainTypeName) { String cons = "\t" + "private " + field.getType().getInterfaceTypeName() + " " + field.getName(); - if (field.getType().equals(DataConstraintModel.typeList)) + if (DataConstraintModel.isListType(field.getType())) cons += " = new ArrayList<>()"; cons += ";"; codes.add(cons); diff --git a/AlgebraicDataflowArchitectureModel/src/algorithms/TypeInference.java b/AlgebraicDataflowArchitectureModel/src/algorithms/TypeInference.java new file mode 100644 index 0000000..9f626af --- /dev/null +++ b/AlgebraicDataflowArchitectureModel/src/algorithms/TypeInference.java @@ -0,0 +1,105 @@ +package algorithms; + +import models.Edge; +import models.Node; +import models.algebra.Expression; +import models.algebra.Term; +import models.algebra.Type; +import models.algebra.Variable; +import models.dataConstraintModel.ChannelGenerator; +import models.dataConstraintModel.ChannelMember; +import models.dataConstraintModel.DataConstraintModel; +import models.dataFlowModel.DataFlowModel; +import models.dataFlowModel.DataflowChannelGenerator; +import models.dataFlowModel.PushPullAttribute; +import models.dataFlowModel.PushPullValue; +import models.dataFlowModel.ResourceDependency; +import models.dataFlowModel.ResourceDependencyGraph; +import models.dataFlowModel.ResourceNode; + +public class TypeInference { + static public void infer(ResourceDependencyGraph graph, DataFlowModel model) { + for (Node n: graph.getNodes()) { + ResourceNode resource = (ResourceNode) n; + Type resourceType = resource.getIdentifierTemplate().getResourceStateType(); + if (resourceType == null || resourceType == DataConstraintModel.typeList) { + if (resource.getIndegree() == 0) { + for (ChannelGenerator c: model.getIOChannelGenerators()) { + for (ChannelMember cm: ((DataflowChannelGenerator) c).getOutputChannelMembers()) { + if (resource.getIdentifierTemplate().equals(cm.getIdentifierTemplate()) + && cm.getStateTransition().getNextStateExpression() instanceof Term) { + updateResourceType(resource, cm); + } + } + } + } else { + for (Edge e: resource.getInEdges()) { + for (ChannelMember cm : ((ResourceDependency) e).getChannelGenerator().getChannelMembers()) { + if (((PushPullAttribute) ((ResourceDependency) e).getAttribute()).getOptions().get(0) == PushPullValue.PUSH + && cm.getStateTransition().getNextStateExpression() instanceof Term) { + updateResourceType(resource, cm); + } + break; + } + } + } + for (Edge e: resource.getOutEdges()) { + for (ChannelMember cm : ((ResourceDependency) e).getChannelGenerator().getChannelMembers()) { + if (((PushPullAttribute) ((ResourceDependency) e).getAttribute()).getOptions().get(0) != PushPullValue.PUSH + && cm.getStateTransition().getNextStateExpression() instanceof Term) { + updateResourceType(resource, cm); + } + break; + } + } + if (resource.getIdentifierTemplate().getResourceStateType() == null) + resource.getIdentifierTemplate().setResourceStateType(DataConstraintModel.typeInt); + } + } + } + + private static void updateResourceType(ResourceNode resource, ChannelMember cm) { + Term rhs = ((Term) cm.getStateTransition().getNextStateExpression()); + if (rhs.getSymbol().equals(DataConstraintModel.cons)) { + Expression listItem = rhs.getChild(0); + if (listItem instanceof Variable) { + Type itemType = null; + if (((Variable) listItem).getType() != null) { + itemType = ((Variable) listItem).getType(); + } else { + if (cm.getStateTransition().getMessageExpression() instanceof Term) { + for (Variable var: ((Term) cm.getStateTransition().getMessageExpression()).getVariables().values()) { + if (((Variable) listItem).getName().equals(var.getName())) { + if (var.getType() != null) { + itemType = var.getType(); + } + } + } + } + if (cm.getStateTransition().getCurStateExpression() instanceof Term) { + for (Variable var: ((Term) cm.getStateTransition().getCurStateExpression()).getVariables().values()) { + if (((Variable) listItem).getName().equals(var.getName())) { + if (var.getType() != null) { + itemType = var.getType(); + } + } + } + } + } + if (itemType == DataConstraintModel.typeInt) { + resource.getIdentifierTemplate().setResourceStateType(DataConstraintModel.typeListOfInt); + } else if (itemType == DataConstraintModel.typeFloat) { + resource.getIdentifierTemplate().setResourceStateType(DataConstraintModel.typeListOfFloat); + } else if (itemType == DataConstraintModel.typeDouble) { + resource.getIdentifierTemplate().setResourceStateType(DataConstraintModel.typeListOfDouble); + } else if (itemType == DataConstraintModel.typeString) { + resource.getIdentifierTemplate().setResourceStateType(DataConstraintModel.typeListOfStr); + } else if (itemType == DataConstraintModel.typeList || itemType == DataConstraintModel.typeListOfList) { + resource.getIdentifierTemplate().setResourceStateType(DataConstraintModel.typeListOfList); + } + } else { + resource.getIdentifierTemplate().setResourceStateType(DataConstraintModel.typeList); + } + } + } +} diff --git a/AlgebraicDataflowArchitectureModel/src/graphicalrefactor/actions/JavaPrototypeGenerateAction.java b/AlgebraicDataflowArchitectureModel/src/graphicalrefactor/actions/JavaPrototypeGenerateAction.java index 7205732..8420a99 100644 --- a/AlgebraicDataflowArchitectureModel/src/graphicalrefactor/actions/JavaPrototypeGenerateAction.java +++ b/AlgebraicDataflowArchitectureModel/src/graphicalrefactor/actions/JavaPrototypeGenerateAction.java @@ -35,6 +35,7 @@ if (graph != null) { DataFlowModel model = editor.getModel(); FinalDecisionOfStoringResourceStates.doDecide(graph); + TypeInference.infer(graph, model); String fileName = editor.getCurFileName(); String mainTypeName = fileName.split("\\.")[0]; boolean exist = false; diff --git a/AlgebraicDataflowArchitectureModel/src/graphicalrefactor/actions/JerseyPrototypeGenerateAction.java b/AlgebraicDataflowArchitectureModel/src/graphicalrefactor/actions/JerseyPrototypeGenerateAction.java index 1bf0de2..b1df27b 100644 --- a/AlgebraicDataflowArchitectureModel/src/graphicalrefactor/actions/JerseyPrototypeGenerateAction.java +++ b/AlgebraicDataflowArchitectureModel/src/graphicalrefactor/actions/JerseyPrototypeGenerateAction.java @@ -36,6 +36,7 @@ if (graph != null) { DataFlowModel model = editor.getModel(); FinalDecisionOfStoringResourceStates.doDecide(graph); + TypeInference.infer(graph, model); String fileName = editor.getCurFileName(); String mainTypeName = fileName.split("\\.")[0]; boolean exist = false; diff --git a/AlgebraicDataflowArchitectureModel/src/models/dataConstraintModel/DataConstraintModel.java b/AlgebraicDataflowArchitectureModel/src/models/dataConstraintModel/DataConstraintModel.java index 762169e..f3a0b57 100644 --- a/AlgebraicDataflowArchitectureModel/src/models/dataConstraintModel/DataConstraintModel.java +++ b/AlgebraicDataflowArchitectureModel/src/models/dataConstraintModel/DataConstraintModel.java @@ -18,9 +18,14 @@ public static final Type typeInt = new Type("Int", "int"); public static final Type typeFloat = new Type("Float", "float"); public static final Type typeDouble = new Type("Double", "double"); - public static final Type typeList = new Type("List", "ArrayList", "List"); public static final Type typeBoolean = new Type("Bool", "boolean"); public static final Type typeString = new Type("Str", "String"); + public static final Type typeList = new Type("List", "ArrayList", "List"); + public static final Type typeListOfStr = new Type("List", "ArrayList", "List"); + public static final Type typeListOfInt = new Type("List", "ArrayList", "List"); + public static final Type typeListOfFloat = new Type("List", "ArrayList", "List"); + public static final Type typeListOfDouble = new Type("List", "ArrayList", "List"); + public static final Type typeListOfList = new Type("List", "ArrayList", "List"); public static final Symbol add = new Symbol(Parser.ADD, 2, Symbol.Type.INFIX); public static final Symbol mul = new Symbol(Parser.MUL, 2, Symbol.Type.INFIX);; public static final Symbol sub = new Symbol(Parser.SUB, 2, Symbol.Type.INFIX); @@ -44,6 +49,7 @@ minus.setInverses(new Symbol[] {minus}); cons.setInverses(new Symbol[] {head, body}); cons.setSignature(new Type[] {typeList, null, typeList}); + contains.setSignature(new Type[] {typeList, null}); } public DataConstraintModel() { @@ -54,9 +60,9 @@ addType(typeInt); addType(typeFloat); addType(typeDouble); - addType(typeList); addType(typeBoolean); addType(typeString); + addType(typeList); symbols = new HashMap<>(); addSymbol(add); addSymbol(mul); @@ -161,4 +167,14 @@ } return out; } + + public static boolean isListType(Type type) { + if (type == typeList) return true; + if (type == typeListOfInt) return true; + if (type == typeListOfFloat) return true; + if (type == typeListOfDouble) return true; + if (type == typeListOfStr) return true; + if (type == typeListOfList) return true; + return false; + } }