diff options
author | Kristóf Marussy <marussy@mit.bme.hu> | 2021-08-20 18:36:01 +0200 |
---|---|---|
committer | Kristóf Marussy <marussy@mit.bme.hu> | 2021-08-20 18:36:01 +0200 |
commit | f0214f17a31d31609e45dbe0dc7dd6ceb98b21fe (patch) | |
tree | b23261e1b58355b706a776639c01fc7cb9a586d7 /language/src | |
parent | renamed TupleRelationView -> KeyOnlyView (diff) | |
download | refinery-f0214f17a31d31609e45dbe0dc7dd6ceb98b21fe.tar.gz refinery-f0214f17a31d31609e45dbe0dc7dd6ceb98b21fe.tar.zst refinery-f0214f17a31d31609e45dbe0dc7dd6ceb98b21fe.zip |
Simplify node naming
Diffstat (limited to 'language/src')
8 files changed, 82 insertions, 108 deletions
diff --git a/language/src/main/java/org/eclipse/viatra/solver/language/Problem.xtext b/language/src/main/java/org/eclipse/viatra/solver/language/Problem.xtext index 9e032a13..d4fa6f35 100644 --- a/language/src/main/java/org/eclipse/viatra/solver/language/Problem.xtext +++ b/language/src/main/java/org/eclipse/viatra/solver/language/Problem.xtext | |||
@@ -8,7 +8,8 @@ Problem: | |||
8 | statements+=Statement*; | 8 | statements+=Statement*; |
9 | 9 | ||
10 | Statement: | 10 | Statement: |
11 | ClassDeclaration | EnumDeclaration | PredicateDefinition | Assertion | NodeValueAssertion | ScopeDeclaration; | 11 | ClassDeclaration | EnumDeclaration | PredicateDefinition | Assertion | NodeValueAssertion | ScopeDeclaration | |
12 | UniqueDeclaration; | ||
12 | 13 | ||
13 | ClassDeclaration: | 14 | ClassDeclaration: |
14 | abstract?="abstract"? "class" | 15 | abstract?="abstract"? "class" |
@@ -25,7 +26,7 @@ EnumLiteral returns Node: | |||
25 | name=Identifier; | 26 | name=Identifier; |
26 | 27 | ||
27 | ReferenceDeclaration: | 28 | ReferenceDeclaration: |
28 | (containment?="contains" | "refers")? | 29 | (-> (containment?="contains" | "refers"))? |
29 | referenceType=[Relation|QualifiedName] | 30 | referenceType=[Relation|QualifiedName] |
30 | ("[" multiplicity=Multiplicity "]")? | 31 | ("[" multiplicity=Multiplicity "]")? |
31 | name=Identifier | 32 | name=Identifier |
@@ -35,7 +36,7 @@ PredicateDefinition: | |||
35 | (error?="error" "pred"? | "pred") | 36 | (error?="error" "pred"? | "pred") |
36 | name=Identifier | 37 | name=Identifier |
37 | "(" (parameters+=Parameter ("," parameters+=Parameter)*)? ")" | 38 | "(" (parameters+=Parameter ("," parameters+=Parameter)*)? ")" |
38 | ("<=>" bodies+=Conjunction (";" bodies+=Conjunction)*)? | 39 | ("<->" bodies+=Conjunction (";" bodies+=Conjunction)*)? |
39 | "."; | 40 | "."; |
40 | 41 | ||
41 | Parameter: | 42 | Parameter: |
@@ -65,6 +66,7 @@ ConstantArgument: | |||
65 | constant=Constant; | 66 | constant=Constant; |
66 | 67 | ||
67 | Assertion: | 68 | Assertion: |
69 | default?="default"? | ||
68 | (relation=[Relation|QualifiedName] | 70 | (relation=[Relation|QualifiedName] |
69 | "(" (arguments+=AssertionArgument ("," arguments+=AssertionArgument)*)? ")" | 71 | "(" (arguments+=AssertionArgument ("," arguments+=AssertionArgument)*)? ")" |
70 | ":" value=LogicValue | | 72 | ":" value=LogicValue | |
@@ -74,16 +76,19 @@ Assertion: | |||
74 | "."; | 76 | "."; |
75 | 77 | ||
76 | AssertionArgument: | 78 | AssertionArgument: |
77 | NodeAssertionArgument | ConstantAssertionArgument; | 79 | NodeAssertionArgument | WildcardAssertionArgument | ConstantAssertionArgument; |
78 | 80 | ||
79 | NodeAssertionArgument: | 81 | NodeAssertionArgument: |
80 | node=[Node|QualifiedName]; | 82 | node=[Node|QualifiedName]; |
81 | 83 | ||
84 | WildcardAssertionArgument: | ||
85 | {WildcardAssertionArgument} "*"; | ||
86 | |||
82 | ConstantAssertionArgument: | 87 | ConstantAssertionArgument: |
83 | constant=Constant; | 88 | constant=Constant; |
84 | 89 | ||
85 | enum LogicValue: | 90 | enum LogicValue: |
86 | TRUE="true" | FALSE="false" | UNKNOWN="unknown"; | 91 | TRUE="true" | FALSE="false" | UNKNOWN="unknown" | ERROR="error"; |
87 | 92 | ||
88 | enum ShortLogicValue returns LogicValue: | 93 | enum ShortLogicValue returns LogicValue: |
89 | FALSE="!" | UNKNOWN="?"; | 94 | FALSE="!" | UNKNOWN="?"; |
@@ -126,14 +131,18 @@ RangeMultiplicity: | |||
126 | ExactMultiplicity: | 131 | ExactMultiplicity: |
127 | exactValue=INT; | 132 | exactValue=INT; |
128 | 133 | ||
134 | UniqueDeclaration: | ||
135 | "unique" nodes+=EnumLiteral ("," nodes+=EnumLiteral)* "."; | ||
136 | |||
129 | UpperBound returns ecore::EInt: | 137 | UpperBound returns ecore::EInt: |
130 | INT | "*"; | 138 | INT | "*"; |
131 | 139 | ||
132 | QualifiedName hidden(): | 140 | QualifiedName hidden(): |
133 | QUOTED_ID | Identifier ("::" Identifier)*; | 141 | Identifier ("::" Identifier)*; |
134 | 142 | ||
135 | Identifier: | 143 | Identifier: |
136 | ID | "true" | "false"; | 144 | ID | "true" | "false" | "unknown" | "error" | "class" | "abstract" | "extends" | "enum" | "pred" | "scope" | |
145 | "unique" | "default" | "problem" | "contains" | "refers"; | ||
137 | 146 | ||
138 | Integer returns ecore::EInt hidden(): | 147 | Integer returns ecore::EInt hidden(): |
139 | "-"? INT; | 148 | "-"? INT; |
@@ -143,18 +152,11 @@ Real returns ecore::EDouble: | |||
143 | 152 | ||
144 | @Override | 153 | @Override |
145 | terminal ID: | 154 | terminal ID: |
146 | ('a'..'z'|'A'..'Z'|'_') ('a'..'z'|'A'..'Z'|'_'|'0'..'9')*; | 155 | ('a'..'z' | 'A'..'Z' | '_') ('a'..'z' | 'A'..'Z' | '_' | '0'..'9')*; |
147 | 156 | ||
148 | terminal EXPONENTIAL: | 157 | terminal EXPONENTIAL: |
149 | INT ("e" | "E") ("+" | "-")? INT; | 158 | INT ("e" | "E") ("+" | "-")? INT; |
150 | 159 | ||
151 | @Override | 160 | @Override |
152 | terminal STRING: | ||
153 | '"' ('\\' . /* 'b'|'t'|'n'|'f'|'r'|'u'|'"'|"'"|'\\' */ | !('\\' | '"'))* '"'; | ||
154 | |||
155 | terminal QUOTED_ID: | ||
156 | "'" ('\\' . /* 'b'|'t'|'n'|'f'|'r'|'u'|'"'|"'"|'\\' */ | !('\\' | "'"))* "'"; | ||
157 | |||
158 | @Override | ||
159 | terminal SL_COMMENT: | 161 | terminal SL_COMMENT: |
160 | ('%' | '//') !('\n' | '\r')* ('\r'? '\n')?; | 162 | ('%' | '//') !('\n' | '\r')* ('\r'? '\n')?; |
diff --git a/language/src/main/java/org/eclipse/viatra/solver/language/ProblemUtil.java b/language/src/main/java/org/eclipse/viatra/solver/language/ProblemUtil.java index 2d7fede6..1581186c 100644 --- a/language/src/main/java/org/eclipse/viatra/solver/language/ProblemUtil.java +++ b/language/src/main/java/org/eclipse/viatra/solver/language/ProblemUtil.java | |||
@@ -16,7 +16,6 @@ import org.eclipse.viatra.solver.language.model.problem.ProblemPackage; | |||
16 | import org.eclipse.viatra.solver.language.model.problem.ReferenceDeclaration; | 16 | import org.eclipse.viatra.solver.language.model.problem.ReferenceDeclaration; |
17 | import org.eclipse.viatra.solver.language.model.problem.Relation; | 17 | import org.eclipse.viatra.solver.language.model.problem.Relation; |
18 | import org.eclipse.viatra.solver.language.model.problem.Variable; | 18 | import org.eclipse.viatra.solver.language.model.problem.Variable; |
19 | import org.eclipse.viatra.solver.language.naming.NamingUtil; | ||
20 | import org.eclipse.viatra.solver.language.scoping.ProblemGlobalScopeProvider; | 19 | import org.eclipse.viatra.solver.language.scoping.ProblemGlobalScopeProvider; |
21 | 20 | ||
22 | import com.google.common.collect.ImmutableList; | 21 | import com.google.common.collect.ImmutableList; |
@@ -32,12 +31,10 @@ public final class ProblemUtil { | |||
32 | return variable.eContainingFeature() == ProblemPackage.Literals.VARIABLE_OR_NODE_ARGUMENT__SINGLETON_VARIABLE; | 31 | return variable.eContainingFeature() == ProblemPackage.Literals.VARIABLE_OR_NODE_ARGUMENT__SINGLETON_VARIABLE; |
33 | } | 32 | } |
34 | 33 | ||
35 | public static boolean isEnumLiteral(Node node) { | 34 | public static boolean isUniqueNode(Node node) { |
36 | return node.eContainingFeature() == ProblemPackage.Literals.ENUM_DECLARATION__LITERALS; | 35 | var containingFeature = node.eContainingFeature(); |
37 | } | 36 | return containingFeature == ProblemPackage.Literals.UNIQUE_DECLARATION__NODES |
38 | 37 | || containingFeature == ProblemPackage.Literals.ENUM_DECLARATION__LITERALS; | |
39 | public static boolean isEnumNode(Node node) { | ||
40 | return NamingUtil.isQuotedName(node.getName()) || isEnumLiteral(node); | ||
41 | } | 38 | } |
42 | 39 | ||
43 | public static boolean isNewNode(Node node) { | 40 | public static boolean isNewNode(Node node) { |
diff --git a/language/src/main/java/org/eclipse/viatra/solver/language/naming/NamingUtil.java b/language/src/main/java/org/eclipse/viatra/solver/language/naming/NamingUtil.java index decc014a..edd455bb 100644 --- a/language/src/main/java/org/eclipse/viatra/solver/language/naming/NamingUtil.java +++ b/language/src/main/java/org/eclipse/viatra/solver/language/naming/NamingUtil.java | |||
@@ -4,8 +4,6 @@ import java.util.regex.Pattern; | |||
4 | 4 | ||
5 | public final class NamingUtil { | 5 | public final class NamingUtil { |
6 | private static final String SINGLETON_VARIABLE_PREFIX = "_"; | 6 | private static final String SINGLETON_VARIABLE_PREFIX = "_"; |
7 | |||
8 | private static final String ENUM_NODE_NAME_QUOTE = "'"; | ||
9 | 7 | ||
10 | private static final Pattern ID_REGEX = Pattern.compile("[_a-zA-Z][_0-9a-zA-Z]*"); | 8 | private static final Pattern ID_REGEX = Pattern.compile("[_a-zA-Z][_0-9a-zA-Z]*"); |
11 | 9 | ||
@@ -20,16 +18,8 @@ public final class NamingUtil { | |||
20 | public static boolean isSingletonVariableName(String name) { | 18 | public static boolean isSingletonVariableName(String name) { |
21 | return name != null && name.startsWith(SINGLETON_VARIABLE_PREFIX); | 19 | return name != null && name.startsWith(SINGLETON_VARIABLE_PREFIX); |
22 | } | 20 | } |
23 | |||
24 | public static boolean isQuotedName(String name) { | ||
25 | return name != null && name.startsWith(ENUM_NODE_NAME_QUOTE) && name.endsWith(ENUM_NODE_NAME_QUOTE); | ||
26 | } | ||
27 | 21 | ||
28 | public static boolean isValidId(String name) { | 22 | public static boolean isValidId(String name) { |
29 | return name != null && ID_REGEX.matcher(name).matches(); | 23 | return name != null && ID_REGEX.matcher(name).matches(); |
30 | } | 24 | } |
31 | |||
32 | public static boolean isValidNodeName(String name) { | ||
33 | return isValidId(name) || isQuotedName(name); | ||
34 | } | ||
35 | } | 25 | } |
diff --git a/language/src/main/java/org/eclipse/viatra/solver/language/resource/NodeNameCollector.java b/language/src/main/java/org/eclipse/viatra/solver/language/resource/NodeNameCollector.java index 597dd92d..e9533c25 100644 --- a/language/src/main/java/org/eclipse/viatra/solver/language/resource/NodeNameCollector.java +++ b/language/src/main/java/org/eclipse/viatra/solver/language/resource/NodeNameCollector.java | |||
@@ -2,24 +2,16 @@ package org.eclipse.viatra.solver.language.resource; | |||
2 | 2 | ||
3 | import java.util.List; | 3 | import java.util.List; |
4 | import java.util.Set; | 4 | import java.util.Set; |
5 | import java.util.function.Predicate; | ||
6 | 5 | ||
7 | import org.eclipse.emf.ecore.EObject; | 6 | import org.eclipse.emf.ecore.EObject; |
8 | import org.eclipse.emf.ecore.EStructuralFeature; | 7 | import org.eclipse.emf.ecore.EStructuralFeature; |
9 | import org.eclipse.viatra.solver.language.model.problem.Argument; | ||
10 | import org.eclipse.viatra.solver.language.model.problem.Assertion; | 8 | import org.eclipse.viatra.solver.language.model.problem.Assertion; |
11 | import org.eclipse.viatra.solver.language.model.problem.AssertionArgument; | 9 | import org.eclipse.viatra.solver.language.model.problem.AssertionArgument; |
12 | import org.eclipse.viatra.solver.language.model.problem.Atom; | ||
13 | import org.eclipse.viatra.solver.language.model.problem.Conjunction; | ||
14 | import org.eclipse.viatra.solver.language.model.problem.Literal; | ||
15 | import org.eclipse.viatra.solver.language.model.problem.NegativeLiteral; | ||
16 | import org.eclipse.viatra.solver.language.model.problem.NodeAssertionArgument; | 10 | import org.eclipse.viatra.solver.language.model.problem.NodeAssertionArgument; |
17 | import org.eclipse.viatra.solver.language.model.problem.NodeValueAssertion; | 11 | import org.eclipse.viatra.solver.language.model.problem.NodeValueAssertion; |
18 | import org.eclipse.viatra.solver.language.model.problem.PredicateDefinition; | ||
19 | import org.eclipse.viatra.solver.language.model.problem.Problem; | 12 | import org.eclipse.viatra.solver.language.model.problem.Problem; |
20 | import org.eclipse.viatra.solver.language.model.problem.ProblemPackage; | 13 | import org.eclipse.viatra.solver.language.model.problem.ProblemPackage; |
21 | import org.eclipse.viatra.solver.language.model.problem.Statement; | 14 | import org.eclipse.viatra.solver.language.model.problem.Statement; |
22 | import org.eclipse.viatra.solver.language.model.problem.VariableOrNodeArgument; | ||
23 | import org.eclipse.viatra.solver.language.naming.NamingUtil; | 15 | import org.eclipse.viatra.solver.language.naming.NamingUtil; |
24 | import org.eclipse.xtext.linking.impl.LinkingHelper; | 16 | import org.eclipse.xtext.linking.impl.LinkingHelper; |
25 | import org.eclipse.xtext.naming.IQualifiedNameConverter; | 17 | import org.eclipse.xtext.naming.IQualifiedNameConverter; |
@@ -64,57 +56,26 @@ public class NodeNameCollector { | |||
64 | collectAssertionNodeNames((Assertion) statement); | 56 | collectAssertionNodeNames((Assertion) statement); |
65 | } else if (statement instanceof NodeValueAssertion) { | 57 | } else if (statement instanceof NodeValueAssertion) { |
66 | collectNodeValueAssertionNodeNames((NodeValueAssertion) statement); | 58 | collectNodeValueAssertionNodeNames((NodeValueAssertion) statement); |
67 | } else if (statement instanceof PredicateDefinition) { | ||
68 | collectPredicateDefinitionNodeNames((PredicateDefinition) statement); | ||
69 | } | 59 | } |
70 | } | 60 | } |
71 | 61 | ||
72 | protected void collectAssertionNodeNames(Assertion assertion) { | 62 | protected void collectAssertionNodeNames(Assertion assertion) { |
73 | for (AssertionArgument argument : assertion.getArguments()) { | 63 | for (AssertionArgument argument : assertion.getArguments()) { |
74 | if (argument instanceof NodeAssertionArgument) { | 64 | if (argument instanceof NodeAssertionArgument) { |
75 | collectNodeNames(argument, ProblemPackage.Literals.NODE_ASSERTION_ARGUMENT__NODE, | 65 | collectNodeNames(argument, ProblemPackage.Literals.NODE_ASSERTION_ARGUMENT__NODE); |
76 | NamingUtil::isValidNodeName); | ||
77 | } | 66 | } |
78 | } | 67 | } |
79 | } | 68 | } |
80 | 69 | ||
81 | protected void collectNodeValueAssertionNodeNames(NodeValueAssertion nodeValueAssertion) { | 70 | protected void collectNodeValueAssertionNodeNames(NodeValueAssertion nodeValueAssertion) { |
82 | collectNodeNames(nodeValueAssertion, ProblemPackage.Literals.NODE_VALUE_ASSERTION__NODE, | 71 | collectNodeNames(nodeValueAssertion, ProblemPackage.Literals.NODE_VALUE_ASSERTION__NODE); |
83 | NamingUtil::isValidNodeName); | ||
84 | } | 72 | } |
85 | 73 | ||
86 | protected void collectPredicateDefinitionNodeNames(PredicateDefinition predicateDefinition) { | 74 | private void collectNodeNames(EObject eObject, EStructuralFeature feature) { |
87 | for (Conjunction body : predicateDefinition.getBodies()) { | ||
88 | for (Literal literal : body.getLiterals()) { | ||
89 | collectLiteralNodeNames(literal); | ||
90 | } | ||
91 | } | ||
92 | } | ||
93 | |||
94 | protected void collectLiteralNodeNames(Literal literal) { | ||
95 | Atom atom = null; | ||
96 | if (literal instanceof Atom) { | ||
97 | atom = (Atom) literal; | ||
98 | } else if (literal instanceof NegativeLiteral) { | ||
99 | var negativeLiteral = (NegativeLiteral) literal; | ||
100 | atom = negativeLiteral.getAtom(); | ||
101 | } | ||
102 | if (atom == null) { | ||
103 | return; | ||
104 | } | ||
105 | for (Argument argument : atom.getArguments()) { | ||
106 | if (argument instanceof VariableOrNodeArgument) { | ||
107 | collectNodeNames(argument, ProblemPackage.Literals.VARIABLE_OR_NODE_ARGUMENT__VARIABLE_OR_NODE, | ||
108 | NamingUtil::isQuotedName); | ||
109 | } | ||
110 | } | ||
111 | } | ||
112 | |||
113 | private void collectNodeNames(EObject eObject, EStructuralFeature feature, Predicate<String> condition) { | ||
114 | List<INode> nodes = NodeModelUtils.findNodesForFeature(eObject, feature); | 75 | List<INode> nodes = NodeModelUtils.findNodesForFeature(eObject, feature); |
115 | for (INode node : nodes) { | 76 | for (INode node : nodes) { |
116 | var nodeName = linkingHelper.getCrossRefNodeAsString(node, true); | 77 | var nodeName = linkingHelper.getCrossRefNodeAsString(node, true); |
117 | if (!condition.test(nodeName)) { | 78 | if (!NamingUtil.isValidId(nodeName)) { |
118 | continue; | 79 | continue; |
119 | } | 80 | } |
120 | var qualifiedName = qualifiedNameConverter.toQualifiedName(nodeName); | 81 | var qualifiedName = qualifiedNameConverter.toQualifiedName(nodeName); |
diff --git a/language/src/main/java/org/eclipse/viatra/solver/language/resource/ProblemLocationInFileProvider.java b/language/src/main/java/org/eclipse/viatra/solver/language/resource/ProblemLocationInFileProvider.java index 94dbdfee..80bbdb0f 100644 --- a/language/src/main/java/org/eclipse/viatra/solver/language/resource/ProblemLocationInFileProvider.java +++ b/language/src/main/java/org/eclipse/viatra/solver/language/resource/ProblemLocationInFileProvider.java | |||
@@ -20,7 +20,7 @@ public class ProblemLocationInFileProvider extends DefaultLocationInFileProvider | |||
20 | } | 20 | } |
21 | 21 | ||
22 | protected ITextRegion getNodeTextRegion(Node node, RegionDescription query) { | 22 | protected ITextRegion getNodeTextRegion(Node node, RegionDescription query) { |
23 | if (ProblemUtil.isEnumLiteral(node)) { | 23 | if (ProblemUtil.isUniqueNode(node)) { |
24 | return super.doGetTextRegion(node, query); | 24 | return super.doGetTextRegion(node, query); |
25 | } | 25 | } |
26 | if (ProblemUtil.isNewNode(node)) { | 26 | if (ProblemUtil.isNewNode(node)) { |
diff --git a/language/src/main/java/org/eclipse/viatra/solver/language/resource/ProblemResourceDescriptionStrategy.java b/language/src/main/java/org/eclipse/viatra/solver/language/resource/ProblemResourceDescriptionStrategy.java index da737e3d..012606d6 100644 --- a/language/src/main/java/org/eclipse/viatra/solver/language/resource/ProblemResourceDescriptionStrategy.java +++ b/language/src/main/java/org/eclipse/viatra/solver/language/resource/ProblemResourceDescriptionStrategy.java | |||
@@ -45,6 +45,7 @@ public class ProblemResourceDescriptionStrategy extends DefaultResourceDescripti | |||
45 | while (parent != null && parent != problem) { | 45 | while (parent != null && parent != problem) { |
46 | var parentQualifiedName = getNameAsQualifiedName(parent); | 46 | var parentQualifiedName = getNameAsQualifiedName(parent); |
47 | if (parentQualifiedName == null) { | 47 | if (parentQualifiedName == null) { |
48 | parent = parent.eContainer(); | ||
48 | continue; | 49 | continue; |
49 | } | 50 | } |
50 | qualifiedName = parentQualifiedName.append(qualifiedName); | 51 | qualifiedName = parentQualifiedName.append(qualifiedName); |
@@ -82,7 +83,7 @@ public class ProblemResourceDescriptionStrategy extends DefaultResourceDescripti | |||
82 | if (eObject instanceof Node) { | 83 | if (eObject instanceof Node) { |
83 | var node = (Node) eObject; | 84 | var node = (Node) eObject; |
84 | // Only enum literals and new nodes are visible across problem files. | 85 | // Only enum literals and new nodes are visible across problem files. |
85 | return ProblemUtil.isEnumLiteral(node) || ProblemUtil.isNewNode(node); | 86 | return ProblemUtil.isUniqueNode(node) || ProblemUtil.isNewNode(node); |
86 | } | 87 | } |
87 | return true; | 88 | return true; |
88 | } | 89 | } |
diff --git a/language/src/test/java/org/eclipse/viatra/solver/language/tests/ProblemTestUtil.xtend b/language/src/test/java/org/eclipse/viatra/solver/language/tests/ProblemTestUtil.xtend index f2aedfd5..b3175659 100644 --- a/language/src/test/java/org/eclipse/viatra/solver/language/tests/ProblemTestUtil.xtend +++ b/language/src/test/java/org/eclipse/viatra/solver/language/tests/ProblemTestUtil.xtend | |||
@@ -17,6 +17,7 @@ import org.eclipse.viatra.solver.language.model.problem.PredicateDefinition | |||
17 | import org.eclipse.viatra.solver.language.model.problem.Problem | 17 | import org.eclipse.viatra.solver.language.model.problem.Problem |
18 | import org.eclipse.viatra.solver.language.model.problem.Variable | 18 | import org.eclipse.viatra.solver.language.model.problem.Variable |
19 | import org.eclipse.viatra.solver.language.model.problem.VariableOrNodeArgument | 19 | import org.eclipse.viatra.solver.language.model.problem.VariableOrNodeArgument |
20 | import org.eclipse.viatra.solver.language.model.problem.UniqueDeclaration | ||
20 | 21 | ||
21 | class ProblemTestUtil { | 22 | class ProblemTestUtil { |
22 | def builtin(Problem it) { | 23 | def builtin(Problem it) { |
@@ -91,6 +92,10 @@ class ProblemTestUtil { | |||
91 | nodes.findFirst[it.name == name] | 92 | nodes.findFirst[it.name == name] |
92 | } | 93 | } |
93 | 94 | ||
95 | def uniqueNode(Problem it, String name) { | ||
96 | statements.filter(UniqueDeclaration).flatMap[nodes].findFirst[it.name == name] | ||
97 | } | ||
98 | |||
94 | def findClass(Problem it, String name) { | 99 | def findClass(Problem it, String name) { |
95 | statements.filter(ClassDeclaration).findFirst[it.name == name] | 100 | statements.filter(ClassDeclaration).findFirst[it.name == name] |
96 | } | 101 | } |
diff --git a/language/src/test/java/org/eclipse/viatra/solver/language/tests/scoping/NodeScopingTest.xtend b/language/src/test/java/org/eclipse/viatra/solver/language/tests/scoping/NodeScopingTest.xtend index 5c34083c..db588e5d 100644 --- a/language/src/test/java/org/eclipse/viatra/solver/language/tests/scoping/NodeScopingTest.xtend +++ b/language/src/test/java/org/eclipse/viatra/solver/language/tests/scoping/NodeScopingTest.xtend | |||
@@ -42,7 +42,7 @@ class NodeScopingTest { | |||
42 | @Test | 42 | @Test |
43 | def void implicitNodeInAssertionTest() { | 43 | def void implicitNodeInAssertionTest() { |
44 | val it = parseHelper.parse(''' | 44 | val it = parseHelper.parse(''' |
45 | pred predicate(node x, node y) <=> node(x). | 45 | pred predicate(node x, node y) <-> node(x). |
46 | predicate(a, a). | 46 | predicate(a, a). |
47 | ?predicate(a, b). | 47 | ?predicate(a, b). |
48 | ''') | 48 | ''') |
@@ -64,9 +64,10 @@ class NodeScopingTest { | |||
64 | assertThat(nodeValueAssertion(0).node, equalTo(node('a'))) | 64 | assertThat(nodeValueAssertion(0).node, equalTo(node('a'))) |
65 | } | 65 | } |
66 | 66 | ||
67 | @Test | ||
67 | def void implicitNodeInPredicateTest() { | 68 | def void implicitNodeInPredicateTest() { |
68 | val it = parseHelper.parse(''' | 69 | val it = parseHelper.parse(''' |
69 | pred predicate(node a) <=> node(b). | 70 | pred predicate(node a) <-> node(b). |
70 | predicate(b). | 71 | predicate(b). |
71 | ''') | 72 | ''') |
72 | assertThat(errors, empty) | 73 | assertThat(errors, empty) |
@@ -75,46 +76,63 @@ class NodeScopingTest { | |||
75 | assertThat(assertion(0).arg(0).node, equalTo(node("b"))) | 76 | assertThat(assertion(0).arg(0).node, equalTo(node("b"))) |
76 | } | 77 | } |
77 | 78 | ||
78 | @Test | 79 | @ParameterizedTest |
79 | def void quotedNodeInAssertionTest() { | 80 | @MethodSource("uniqueNodeReferenceSource") |
81 | def void uniqueNodeInAssertionTest(String qualifiedNamePrefix, boolean namedProblem) { | ||
80 | val it = parseHelper.parse(''' | 82 | val it = parseHelper.parse(''' |
81 | pred predicate(node x, node y) <=> node(x). | 83 | «IF namedProblem»problem test.«ENDIF» |
82 | predicate('a', 'a'). | 84 | unique a, b. |
83 | ?predicate('a', 'b'). | 85 | pred predicate(node x, node y) <-> node(x). |
86 | predicate(«qualifiedNamePrefix»a, «qualifiedNamePrefix»a). | ||
87 | ?predicate(«qualifiedNamePrefix»a, «qualifiedNamePrefix»b). | ||
84 | ''') | 88 | ''') |
85 | assertThat(errors, empty) | 89 | assertThat(errors, empty) |
86 | assertThat(nodeNames, hasItems("'a'", "'b'")) | 90 | assertThat(nodeNames, empty) |
87 | assertThat(assertion(0).arg(0).node, equalTo(node("'a'"))) | 91 | assertThat(assertion(0).arg(0).node, equalTo(uniqueNode('a'))) |
88 | assertThat(assertion(0).arg(1).node, equalTo(node("'a'"))) | 92 | assertThat(assertion(0).arg(1).node, equalTo(uniqueNode('a'))) |
89 | assertThat(assertion(1).arg(0).node, equalTo(node("'a'"))) | 93 | assertThat(assertion(1).arg(0).node, equalTo(uniqueNode('a'))) |
90 | assertThat(assertion(1).arg(1).node, equalTo(node("'b'"))) | 94 | assertThat(assertion(1).arg(1).node, equalTo(uniqueNode('b'))) |
91 | } | 95 | } |
92 | 96 | ||
93 | @Test | 97 | @ParameterizedTest |
94 | def void quotedNodeInNodeValueAssertionTest() { | 98 | @MethodSource("uniqueNodeReferenceSource") |
99 | def void uniqueNodeInNodeValueAssertionTest(String qualifiedNamePrefix, boolean namedProblem) { | ||
95 | val it = parseHelper.parse(''' | 100 | val it = parseHelper.parse(''' |
96 | 'a': 16. | 101 | «IF namedProblem»problem test.«ENDIF» |
102 | unique a. | ||
103 | «qualifiedNamePrefix»a: 16. | ||
97 | ''') | 104 | ''') |
98 | assertThat(errors, empty) | 105 | assertThat(errors, empty) |
99 | assertThat(nodeNames, hasItems("'a'")) | 106 | assertThat(nodeNames, empty) |
100 | assertThat(nodeValueAssertion(0).node, equalTo(node("'a'"))) | 107 | assertThat(nodeValueAssertion(0).node, equalTo(uniqueNode('a'))) |
101 | } | 108 | } |
102 | 109 | ||
103 | @Test | 110 | @ParameterizedTest |
104 | def void quotedNodeInPredicateTest() { | 111 | @MethodSource("uniqueNodeReferenceSource") |
112 | def void uniqueNodeInPredicateTest(String qualifiedNamePrefix, boolean namedProblem) { | ||
105 | val it = parseHelper.parse(''' | 113 | val it = parseHelper.parse(''' |
106 | pred predicate(node a) <=> node('b'). | 114 | «IF namedProblem»problem test.«ENDIF» |
115 | unique b. | ||
116 | pred predicate(node a) <-> node(«qualifiedNamePrefix»b). | ||
107 | ''') | 117 | ''') |
108 | assertThat(errors, empty) | 118 | assertThat(errors, empty) |
109 | assertThat(nodeNames, hasItem("'b'")) | 119 | assertThat(nodeNames, empty) |
110 | assertThat(pred("predicate").conj(0).lit(0).arg(0).node, equalTo(node("'b'"))) | 120 | assertThat(pred("predicate").conj(0).lit(0).arg(0).node, equalTo(uniqueNode("b"))) |
121 | } | ||
122 | |||
123 | static def uniqueNodeReferenceSource() { | ||
124 | Stream.of( | ||
125 | Arguments.of("", false), | ||
126 | Arguments.of("", true), | ||
127 | Arguments.of("test::", true) | ||
128 | ) | ||
111 | } | 129 | } |
112 | 130 | ||
113 | @ParameterizedTest | 131 | @ParameterizedTest |
114 | @MethodSource("builtInNodeReferencesSource") | 132 | @MethodSource("builtInNodeReferencesSource") |
115 | def void builtInNodeTest(String qualifiedName) { | 133 | def void builtInNodeTest(String qualifiedName) { |
116 | val it = parseHelper.parse(''' | 134 | val it = parseHelper.parse(''' |
117 | pred predicate(node x) <=> node(x). | 135 | pred predicate(node x) <-> node(x). |
118 | predicate(«qualifiedName»). | 136 | predicate(«qualifiedName»). |
119 | ''') | 137 | ''') |
120 | assertThat(errors, empty) | 138 | assertThat(errors, empty) |
@@ -137,7 +155,7 @@ class NodeScopingTest { | |||
137 | @MethodSource("builtInNodeReferencesSource") | 155 | @MethodSource("builtInNodeReferencesSource") |
138 | def void builtInNodeInPredicateTest(String qualifiedName) { | 156 | def void builtInNodeInPredicateTest(String qualifiedName) { |
139 | val it = parseHelper.parse(''' | 157 | val it = parseHelper.parse(''' |
140 | pred predicate(node x) <=> node(«qualifiedName»). | 158 | pred predicate(node x) <-> node(«qualifiedName»). |
141 | ''') | 159 | ''') |
142 | assertThat(errors, empty) | 160 | assertThat(errors, empty) |
143 | assertThat(pred("predicate").conj(0).lit(0).arg(0).node, equalTo(builtin.findClass('int').newNode)) | 161 | assertThat(pred("predicate").conj(0).lit(0).arg(0).node, equalTo(builtin.findClass('int').newNode)) |
@@ -156,7 +174,7 @@ class NodeScopingTest { | |||
156 | val it = parseHelper.parse(''' | 174 | val it = parseHelper.parse(''' |
157 | «IF namedProblem»problem test.«ENDIF» | 175 | «IF namedProblem»problem test.«ENDIF» |
158 | class Foo. | 176 | class Foo. |
159 | pred predicate(node x) <=> node(x). | 177 | pred predicate(node x) <-> node(x). |
160 | predicate(«qualifiedName»). | 178 | predicate(«qualifiedName»). |
161 | ''') | 179 | ''') |
162 | assertThat(errors, empty) | 180 | assertThat(errors, empty) |
@@ -183,7 +201,7 @@ class NodeScopingTest { | |||
183 | val it = parseHelper.parse(''' | 201 | val it = parseHelper.parse(''' |
184 | «IF namedProblem»problem test.«ENDIF» | 202 | «IF namedProblem»problem test.«ENDIF» |
185 | class Foo. | 203 | class Foo. |
186 | pred predicate(node x) <=> node(«qualifiedName»). | 204 | pred predicate(node x) <-> node(«qualifiedName»). |
187 | ''') | 205 | ''') |
188 | assertThat(errors, empty) | 206 | assertThat(errors, empty) |
189 | assertThat(pred("predicate").conj(0).lit(0).arg(0).node, equalTo(findClass('Foo').newNode)) | 207 | assertThat(pred("predicate").conj(0).lit(0).arg(0).node, equalTo(findClass('Foo').newNode)) |
@@ -201,7 +219,7 @@ class NodeScopingTest { | |||
201 | def void newNodeIsNotSpecial() { | 219 | def void newNodeIsNotSpecial() { |
202 | val it = parseHelper.parse(''' | 220 | val it = parseHelper.parse(''' |
203 | class Foo. | 221 | class Foo. |
204 | pred predicate(node x) <=> node(x). | 222 | pred predicate(node x) <-> node(x). |
205 | predicate(new). | 223 | predicate(new). |
206 | ''') | 224 | ''') |
207 | assertThat(errors, empty) | 225 | assertThat(errors, empty) |
@@ -215,7 +233,7 @@ class NodeScopingTest { | |||
215 | val it = parseHelper.parse(''' | 233 | val it = parseHelper.parse(''' |
216 | «IF namedProblem»problem test.«ENDIF» | 234 | «IF namedProblem»problem test.«ENDIF» |
217 | enum Foo { alpha, beta } | 235 | enum Foo { alpha, beta } |
218 | pred predicate(Foo a) <=> node(a). | 236 | pred predicate(Foo a) <-> node(a). |
219 | predicate(«qualifiedName»). | 237 | predicate(«qualifiedName»). |
220 | ''') | 238 | ''') |
221 | assertThat(errors, empty) | 239 | assertThat(errors, empty) |
@@ -242,7 +260,7 @@ class NodeScopingTest { | |||
242 | val it = parseHelper.parse(''' | 260 | val it = parseHelper.parse(''' |
243 | «IF namedProblem»problem test.«ENDIF» | 261 | «IF namedProblem»problem test.«ENDIF» |
244 | enum Foo { alpha, beta } | 262 | enum Foo { alpha, beta } |
245 | pred predicate(Foo a) <=> node(«qualifiedName»). | 263 | pred predicate(Foo a) <-> node(«qualifiedName»). |
246 | ''') | 264 | ''') |
247 | assertThat(errors, empty) | 265 | assertThat(errors, empty) |
248 | assertThat(nodes, empty) | 266 | assertThat(nodes, empty) |
@@ -264,7 +282,7 @@ class NodeScopingTest { | |||
264 | @MethodSource("builtInEnumLiteralReferencesSource") | 282 | @MethodSource("builtInEnumLiteralReferencesSource") |
265 | def void builtInEnumLiteralTest(String qualifiedName) { | 283 | def void builtInEnumLiteralTest(String qualifiedName) { |
266 | val it = parseHelper.parse(''' | 284 | val it = parseHelper.parse(''' |
267 | pred predicate(node a) <=> node(a). | 285 | pred predicate(node a) <-> node(a). |
268 | predicate(«qualifiedName»). | 286 | predicate(«qualifiedName»). |
269 | ''') | 287 | ''') |
270 | assertThat(errors, empty) | 288 | assertThat(errors, empty) |
@@ -287,7 +305,7 @@ class NodeScopingTest { | |||
287 | @MethodSource("builtInEnumLiteralReferencesSource") | 305 | @MethodSource("builtInEnumLiteralReferencesSource") |
288 | def void bultInEnumLiteralInPredicateTest(String qualifiedName) { | 306 | def void bultInEnumLiteralInPredicateTest(String qualifiedName) { |
289 | val it = parseHelper.parse(''' | 307 | val it = parseHelper.parse(''' |
290 | pred predicate() <=> node(«qualifiedName»). | 308 | pred predicate() <-> node(«qualifiedName»). |
291 | ''') | 309 | ''') |
292 | assertThat(errors, empty) | 310 | assertThat(errors, empty) |
293 | assertThat(pred("predicate").conj(0).lit(0).arg(0).node, equalTo(builtin.findEnum("bool").literal("true"))) | 311 | assertThat(pred("predicate").conj(0).lit(0).arg(0).node, equalTo(builtin.findEnum("bool").literal("true"))) |