source: trunk/autoquest-core-tasktrees/src/main/java/de/ugoe/cs/autoquest/tasktrees/taskequality/TaskAndIterationComparisonRule.java @ 1294

Last change on this file since 1294 was 1294, checked in by pharms, 11 years ago
  • rework of task model to move event instance stuff to task instances
  • introduction of sequence, selection, iteration and optional instances
File size: 12.8 KB
Line 
1//   Copyright 2012 Georg-August-Universität Göttingen, Germany
2//
3//   Licensed under the Apache License, Version 2.0 (the "License");
4//   you may not use this file except in compliance with the License.
5//   You may obtain a copy of the License at
6//
7//       http://www.apache.org/licenses/LICENSE-2.0
8//
9//   Unless required by applicable law or agreed to in writing, software
10//   distributed under the License is distributed on an "AS IS" BASIS,
11//   WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12//   See the License for the specific language governing permissions and
13//   limitations under the License.
14
15package de.ugoe.cs.autoquest.tasktrees.taskequality;
16
17import de.ugoe.cs.autoquest.tasktrees.treeifc.IIteration;
18import de.ugoe.cs.autoquest.tasktrees.treeifc.IIterationInstance;
19import de.ugoe.cs.autoquest.tasktrees.treeifc.ITask;
20import de.ugoe.cs.autoquest.tasktrees.treeifc.ITaskInstance;
21
22/**
23 * <p>
24 * This class is capable of comparing any task which is not an iteration with an
25 * iteration. This is needed, because iterations may iterate exactly that task. In this
26 * case, the iteration would be equal to that task if it was executed exactly once. The rule
27 * returns lexically equal, it the child of the iteration is lexically equal to the task
28 * or if the child of the iteration is a selection and this selections contains a lexically equal
29 * task. The same applies for syntactical and semantical equality.
30 * </p>
31
32 * @author Patrick Harms
33 */
34public class TaskAndIterationComparisonRule implements TaskComparisonRule {
35   
36    /* (non-Javadoc)
37     * @see TaskComparisonRule#isApplicable(ITask, ITask)
38     */
39    @Override
40    public boolean isApplicable(ITask task1, ITask task2) {
41        return ((task1 instanceof IIteration) && (!(task2 instanceof IIteration))) ||
42               ((task2 instanceof IIteration) && (!(task1 instanceof IIteration)));
43    }
44
45    /* (non-Javadoc)
46     * @see TaskComparisonRule#areLexicallyEqual(ITask, ITask)
47     */
48    @Override
49    public boolean areLexicallyEqual(ITask task1, ITask task2) {
50        TaskEquality equality = getEquality(task1, task2, TaskEquality.LEXICALLY_EQUAL);
51        return (equality != null) && (equality.isAtLeast(TaskEquality.LEXICALLY_EQUAL));
52    }
53
54    /* (non-Javadoc)
55     * @see TaskComparisonRule#areSyntacticallyEqual(ITask, ITask)
56     */
57    @Override
58    public boolean areSyntacticallyEqual(ITask task1, ITask task2) {
59        TaskEquality equality = getEquality(task1, task2, TaskEquality.SYNTACTICALLY_EQUAL);
60        return (equality != null) && (equality.isAtLeast(TaskEquality.SYNTACTICALLY_EQUAL));
61    }
62
63    /* (non-Javadoc)
64     * @see TaskComparisonRule#areSemanticallyEqual(ITask, ITask)
65     */
66    @Override
67    public boolean areSemanticallyEqual(ITask task1, ITask task2) {
68        TaskEquality equality = getEquality(task1, task2, TaskEquality.SEMANTICALLY_EQUAL);
69        return (equality != null) && (equality.isAtLeast(TaskEquality.SEMANTICALLY_EQUAL));
70    }
71
72    /* (non-Javadoc)
73     * @see TaskComparisonRule#compare(ITask, ITask)
74     */
75    @Override
76    public TaskEquality compare(ITask task1, ITask task2) {
77        return getEquality(task1, task2, null);
78    }
79
80    /* (non-Javadoc)
81     * @see TaskComparisonRule#isApplicable(ITaskInstance, ITaskInstance)
82     */
83    @Override
84    public boolean isApplicable(ITaskInstance instance1, ITaskInstance instance2) {
85        return isApplicable(instance1.getTask(), instance2.getTask());
86    }
87
88    /* (non-Javadoc)
89     * @see TaskComparisonRule#areLexicallyEqual(ITaskInstance, ITaskInstance)
90     */
91    @Override
92    public boolean areLexicallyEqual(ITaskInstance instance1, ITaskInstance instance2) {
93        TaskEquality equality = getEquality(instance1, instance2, TaskEquality.LEXICALLY_EQUAL);
94        return (equality != null) && (equality.isAtLeast(TaskEquality.LEXICALLY_EQUAL));
95    }
96
97    /* (non-Javadoc)
98     * @see TaskComparisonRule#areSyntacticallyEqual(ITaskInstance, ITaskInstance)
99     */
100    @Override
101    public boolean areSyntacticallyEqual(ITaskInstance instance1, ITaskInstance instance2) {
102        TaskEquality equality = getEquality(instance1, instance2, TaskEquality.SYNTACTICALLY_EQUAL);
103        return (equality != null) && (equality.isAtLeast(TaskEquality.SYNTACTICALLY_EQUAL));
104    }
105
106    /* (non-Javadoc)
107     * @see TaskComparisonRule#areSemanticallyEqual(ITaskInstance, ITaskInstance)
108     */
109    @Override
110    public boolean areSemanticallyEqual(ITaskInstance instance1, ITaskInstance instance2) {
111        TaskEquality equality = getEquality(instance1, instance2, TaskEquality.SEMANTICALLY_EQUAL);
112        return (equality != null) && (equality.isAtLeast(TaskEquality.SEMANTICALLY_EQUAL));
113    }
114
115    /* (non-Javadoc)
116     * @see TaskComparisonRule#compare(ITaskInstance, ITaskInstance)
117     */
118    @Override
119    public TaskEquality compare(ITaskInstance instance1, ITaskInstance instance2) {
120        return getEquality(instance1, instance2, null);
121    }
122
123    /**
124     * <p>
125     * compares two tasks with each other checking for the provided required level of
126     * equality. One of the tasks must be an iteration, the other one not. If this is not the
127     * case, the method returns null. The returned equality level is at most lexical equality
128     * as the iteration can not be identical to something not being an iteration.
129     * </p>
130     *
131     * @param task1                 the first task to be compared
132     * @param task2                 the second task to be compared
133     * @param requiredEqualityLevel the equality level to be checked for
134     *
135     * @return the determined equality.
136     */
137    private TaskEquality getEquality(ITask task1, ITask task2, TaskEquality requiredEqualityLevel) {
138        IIteration iteration = null;
139        ITask task = null;
140       
141        if (task1 instanceof IIteration) {
142            if (task2 instanceof IIteration) {
143                // the rule is not responsible for two iterations
144                return null;
145            }
146           
147            iteration = (IIteration) task1;
148            task = task2;
149        }
150        else if (task2 instanceof IIteration) {
151            if (task1 instanceof IIteration) {
152                // the rule is not responsible for two iterations
153                return null;
154            }
155           
156            iteration = (IIteration) task2;
157            task = task1;
158        }
159        else {
160            return null;
161        }
162
163        ITask child = iteration.getMarkedTask();
164       
165        // now, that we found the iteration and the task, lets compare the child of the iteration
166        // with the task.
167        if (child == null) {
168            return null;
169        }
170
171        TaskEquality taskEquality = callRuleManager(child, task, requiredEqualityLevel);
172
173        // although the subtask may be identical to the task, we can not return identical, as
174        // the iteration is not identical to the task, but at most lexically equal
175        if (taskEquality == TaskEquality.IDENTICAL) {
176            return TaskEquality.LEXICALLY_EQUAL;
177        }
178        else {
179            return taskEquality;
180        }
181
182    }
183   
184    /**
185     * <p>
186     * used to to call the task equality rule manager for the comparison of the two provided
187     * children. If no required equality level is provided, than the most concrete equality is
188     * returned. Otherwise, the required equality is returned as long as the children are equal
189     * on that level.
190     * </p>
191     *
192     * @param child1                the first task to be compared
193     * @param child2                the second task to be compared
194     * @param requiredEqualityLevel the equality level to be checked for
195     *
196     * @return the determined equality
197     */
198    private TaskEquality callRuleManager(ITask        child1,
199                                         ITask        child2,
200                                         TaskEquality requiredEqualityLevel)
201    {
202        if (requiredEqualityLevel == null) {
203            return TaskEqualityRuleManager.getInstance().compare(child1, child2);
204        }
205        else if (TaskEqualityRuleManager.getInstance().areAtLeastEqual
206                     (child1, child2, requiredEqualityLevel))
207        {
208            return requiredEqualityLevel;
209        }
210        else {
211            return TaskEquality.UNEQUAL;
212        }
213    }
214
215    /**
216     * <p>
217     * compares two task instances with each other checking for the provided required level of
218     * equality. One of the task instances must be a iteration, the other one not. If this is not
219     * the case, the method returns null. The returned equality level is at most lexical equality
220     * as the iteration can not be identical to something not being a iteration.
221     * </p>
222     *
223     * @param taskInstance1         the first task instance to be compared
224     * @param taskInstance2         the second task instance to be compared
225     * @param requiredEqualityLevel the equality level to be checked for
226     *
227     * @return the determined equality.
228     */
229    private TaskEquality getEquality(ITaskInstance taskInstance1,
230                                     ITaskInstance taskInstance2,
231                                     TaskEquality  requiredEqualityLevel)
232    {
233        IIterationInstance iteration = null;
234        ITaskInstance task = null;
235       
236        if (taskInstance1 instanceof IIterationInstance) {
237            if (taskInstance2 instanceof IIterationInstance) {
238                // the rule is not responsible for two iterations
239                return null;
240            }
241           
242            iteration = (IIterationInstance) taskInstance1;
243            task = taskInstance2;
244        }
245        else if (taskInstance2 instanceof IIterationInstance) {
246            if (taskInstance1 instanceof IIterationInstance) {
247                // the rule is not responsible for two iterations
248                return null;
249            }
250           
251            iteration = (IIterationInstance) taskInstance2;
252            task = taskInstance1;
253        }
254        else {
255            return null;
256        }
257
258        // now, that we found the iteration and the task, lets compare the children of the iteration
259        // with the task.
260       
261        if (iteration.size() < 1) {
262            return null;
263        }
264
265        TaskEquality mostConcreteNodeEquality = null;
266       
267        for (ITaskInstance child : iteration) {
268            TaskEquality taskEquality = callRuleManager(child, task, requiredEqualityLevel);
269           
270            if (taskEquality != TaskEquality.UNEQUAL) {
271                if (mostConcreteNodeEquality == null) {
272                    mostConcreteNodeEquality = taskEquality;
273                }
274                else if (mostConcreteNodeEquality.isAtLeast(taskEquality)) {
275                    mostConcreteNodeEquality = taskEquality;
276                   
277                }
278               
279                if ((requiredEqualityLevel != null) &&
280                    (mostConcreteNodeEquality.isAtLeast(requiredEqualityLevel)))
281                {
282                    // if we found one child of the selection that is as equal as required, then
283                    // we can consider the selection to be sufficiently equal to the other task.
284                    // So we break up checking further children.
285                    break;
286                }
287            }
288        }
289       
290        // although the subtask may be identical to the task, we can not return identical, as
291        // the selection is not identical to the task, but at most lexically equal
292        if (mostConcreteNodeEquality == TaskEquality.IDENTICAL) {
293            return TaskEquality.LEXICALLY_EQUAL;
294        }
295        else {
296            return mostConcreteNodeEquality;
297        }
298
299    }
300   
301    /**
302     * <p>
303     * used to to call the task equality rule manager for the comparison of the two provided
304     * children. If no required equality level is provided, than the most concrete equality is
305     * returned. Otherwise, the required equality is returned as long as the children are equal
306     * on that level.
307     * </p>
308     *
309     * @param taskInstance1         the first task instance to be compared
310     * @param taskInstance2         the second task instance to be compared
311     * @param requiredEqualityLevel the equality level to be checked for
312     *
313     * @return the determined equality
314     */
315    private TaskEquality callRuleManager(ITaskInstance taskInstance1,
316                                         ITaskInstance taskInstance2,
317                                         TaskEquality  requiredEqualityLevel)
318    {
319        if (requiredEqualityLevel == null) {
320            return TaskEqualityRuleManager.getInstance().compare(taskInstance1, taskInstance2);
321        }
322        else if (TaskEqualityRuleManager.getInstance().areAtLeastEqual
323                     (taskInstance1, taskInstance2, requiredEqualityLevel))
324        {
325            return requiredEqualityLevel;
326        }
327        else {
328            return TaskEquality.UNEQUAL;
329        }
330    }
331}
Note: See TracBrowser for help on using the repository browser.