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

Last change on this file since 2255 was 2218, checked in by pharms, 7 years ago
  • java doc issues removal
  • Property svn:executable set to *
File size: 16.2 KB
RevLine 
[1113]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
[1146]15package de.ugoe.cs.autoquest.tasktrees.taskequality;
[439]16
17import java.util.ArrayList;
18import java.util.List;
19
[1146]20import de.ugoe.cs.autoquest.tasktrees.treeifc.ITask;
[1294]21import de.ugoe.cs.autoquest.tasktrees.treeifc.ITaskInstance;
[439]22
23/**
[557]24 * <p>
[1294]25 * The task equality rule manager is capable of comparing tasks and task instances based on its
26 * internal list of comparison rules. These rules are asked for comparing the two provided tasks or
27 * task instance. If a rule returns a task equality other than null, this equality is returned.
28 * Otherwise the next rule is asked.
[557]29 * </p>
[439]30 *
[1294]31 * @author Patrick Harms
[439]32 */
[1146]33public class TaskEqualityRuleManager {
[1189]34   
35    /**
36     * <p>
37     * the singleton instance of this class
38     * </p>
39     */
40    private static final TaskEqualityRuleManager instance = new TaskEqualityRuleManager();
[439]41
[1154]42    /**
43     * <p>
44     * the rules that can be used for comparing tasks
45     * </p>
46     */
[1146]47    private List<TaskComparisonRule> mRuleIndex = null;
[439]48
[557]49    /**
50     * <p>
[1146]51     * initializes the task equality rule manager by filling the internal list of comparison rules.
[557]52     * </p>
53     */
[1189]54    private TaskEqualityRuleManager() {
[1146]55        mRuleIndex = new ArrayList<TaskComparisonRule>();
56        mRuleIndex.add(new TaskIdentityRule());
[807]57        mRuleIndex.add(new GUIEventTaskComparisonRule());
[2161]58        mRuleIndex.add(new InefficientActionsComparisonRule());
[807]59        mRuleIndex.add(new EventTaskComparisonRule());
[1190]60        mRuleIndex.add(new IterationComparisonRule());
[1887]61        mRuleIndex.add(new OptionalComparisonRule());
[1190]62        mRuleIndex.add(new SequenceComparisonRule());
63        mRuleIndex.add(new SelectionComparisonRule());
64        mRuleIndex.add(new TaskAndIterationComparisonRule());
[1887]65        mRuleIndex.add(new TaskAndOptionalComparisonRule());
[1190]66        mRuleIndex.add(new TaskAndSelectionComparisonRule());
[557]67    }
[439]68
[1189]69
[557]70    /**
71     * <p>
[1189]72     * returns the singleton instance of this class
73     * </p>
74     *
75     * @return as described
76     */
77    public static TaskEqualityRuleManager getInstance() {
78        return instance;
79    }
80
81    /**
82     * <p>
[1146]83     * this method performs a comparison of the two provided tasks. It iterates its internal
84     * comparison rules. If the first rule returns a task equality other than null,
[557]85     * this equality is returned. Otherwise the next rule is tried. If no rule returns an equality
86     * <code>NodeEquality.UNEQUAL</code> is returned.
87     * </p>
88     *
[1146]89     * @param task1 the first task to be compared
90     * @param task2 the second task to be compared
[557]91     *
92     * @return as described
93     *
[2218]94     * @throws IllegalStateException in the case, the object is not correctly initialized
[557]95     */
[1146]96    public TaskEquality compare(ITask task1, ITask task2)
[557]97        throws IllegalStateException
[439]98    {
[557]99        if (mRuleIndex == null) {
100            throw new IllegalStateException("not initialized");
101        }
102       
[1146]103        // LOG.info("checking for equality of " + task1 + " and " + task2);
104        TaskEquality taskEquality = null;
[557]105
[1146]106        for (TaskComparisonRule rule : mRuleIndex) {
107            if (rule.isApplicable(task1, task2)) {
108                taskEquality = rule.compare(task1, task2);
109                if (taskEquality != null) {
[1125]110                    // LOG.warning("used rule " + rule + " for equality check");
[1146]111                    return taskEquality;
[1125]112                }
[557]113            }
114        }
115
[1146]116        // LOG.warning("no rule could be applied --> handling tasks as unequal");
[557]117
[1146]118        return TaskEquality.UNEQUAL;
[439]119    }
120
[1125]121    /**
122     * <p>
[1154]123     * this method two tasks with respect to the fiven equality level and returns true, if this
124     * level is given.
[1125]125     * </p>
[1154]126     *
127     * @param task1         the first task to be compared
128     * @param task2         the second task to be compared
129     * @param equalityLevel the level of equality to be checked for
130     *
131     * @return as described
132     *
[2218]133     * @throws IllegalStateException in the case, the object is not correctly initialized
[1125]134     */
[1146]135    public boolean areAtLeastEqual(ITask task1, ITask task2, TaskEquality equalityLevel) {
[1125]136        if (equalityLevel == null) {
137            throw new IllegalArgumentException("required equality level must not be null");
138        }
139       
140        switch (equalityLevel) {
141            case IDENTICAL:
[1146]142                return areIdentical(task1, task2);
[1125]143            case LEXICALLY_EQUAL:
[1146]144                return areLexicallyEqual(task1, task2);
[1125]145            case SYNTACTICALLY_EQUAL:
[1146]146                return areSyntacticallyEqual(task1, task2);
[1125]147            case SEMANTICALLY_EQUAL:
[1146]148                return areSemanticallyEqual(task1, task2);
[1125]149            case UNEQUAL:
[1146]150                return !areSemanticallyEqual(task1, task2);
[1125]151            default:
152                throw new IllegalArgumentException("unknown required equality: " + equalityLevel);
153        }
154    }
155
156    /**
157     * <p>
[1154]158     * this method checks if the two given tasks are identical. For this, it iterates its internal
159     * comparison rules. If the first rule returns true, than this method returns true as well.
160     * If no rule returns true, this method returns false.
[1125]161     * </p>
[1154]162     *
163     * @param task1 the first task to be compared
164     * @param task2 the second task to be compared
165     *
166     * @return as described
167     *
[2218]168     * @throws IllegalStateException in the case, the object is not correctly initialized
[1125]169     */
[1146]170    public boolean areIdentical(ITask task1, ITask task2) {
[1125]171        if (mRuleIndex == null) {
172            throw new IllegalStateException("not initialized");
173        }
174       
[1146]175        for (TaskComparisonRule rule : mRuleIndex) {
176            if (rule.isApplicable(task1, task2) && rule.areLexicallyEqual(task1, task2)) {
[1125]177                 return true;
178            }
179        }
180
181        return false;
182    }
183
184    /**
185     * <p>
[1154]186     * this method checks if the two given tasks are lexically equal. For this, it iterates its
187     * internal comparison rules. If the first rule returns true, than this method returns true
188     * as well. If no rule returns true, this method returns false.
[1125]189     * </p>
[1154]190     *
191     * @param task1 the first task to be compared
192     * @param task2 the second task to be compared
193     *
194     * @return as described
195     *
[2218]196     * @throws IllegalStateException in the case, the object is not correctly initialized
[1125]197     */
[1146]198    public boolean areLexicallyEqual(ITask task1, ITask task2) {
[1125]199        if (mRuleIndex == null) {
200            throw new IllegalStateException("not initialized");
201        }
202       
[1146]203        for (TaskComparisonRule rule : mRuleIndex) {
204            if (rule.isApplicable(task1, task2) && rule.areLexicallyEqual(task1, task2)) {
[1125]205                 return true;
206            }
207        }
208
209        return false;
210    }
211
212    /**
213     * <p>
[1154]214     * this method checks if the two given tasks are syntactically equal. For this, it iterates its
215     * internal comparison rules. If the first rule returns true, than this method returns true
216     * as well. If no rule returns true, this method returns false.
[1125]217     * </p>
[1154]218     *
219     * @param task1 the first task to be compared
220     * @param task2 the second task to be compared
221     *
222     * @return as described
223     *
[2218]224     * @throws IllegalStateException in the case, the object is not correctly initialized
[1125]225     */
[1146]226    public boolean areSyntacticallyEqual(ITask task1, ITask task2) {
[1125]227        if (mRuleIndex == null) {
228            throw new IllegalStateException("not initialized");
229        }
230       
[1146]231        for (TaskComparisonRule rule : mRuleIndex) {
232            if (rule.isApplicable(task1, task2) && rule.areSyntacticallyEqual(task1, task2)) {
[1125]233                 return true;
234            }
235        }
236
237        return false;
238    }
239
240    /**
241     * <p>
[1154]242     * this method checks if the two given tasks are semantically equal. For this, it iterates its
243     * internal comparison rules. If the first rule returns true, than this method returns true
244     * as well. If no rule returns true, this method returns false.
[1125]245     * </p>
[1154]246     *
247     * @param task1 the first task to be compared
248     * @param task2 the second task to be compared
249     *
250     * @return as described
251     *
[2218]252     * @throws IllegalStateException in the case, the object is not correctly initialized
[1125]253     */
[1146]254    public boolean areSemanticallyEqual(ITask task1, ITask task2) {
[1125]255        if (mRuleIndex == null) {
256            throw new IllegalStateException("not initialized");
257        }
258       
[1146]259        for (TaskComparisonRule rule : mRuleIndex) {
260            if (rule.isApplicable(task1, task2) && rule.areSemanticallyEqual(task1, task2)) {
[1125]261                 return true;
262            }
263        }
264
265        return false;
266    }
267
[1294]268    /**
269     * <p>
270     * this method performs a comparison of the two provided task instances. It iterates its
271     * internal comparison rules. If the first rule returns a task instance equality other than
272     * null, this equality is returned. Otherwise the next rule is tried. If no rule returns an
273     * equality <code>TaskEquality.UNEQUAL</code> is returned.
274     * </p>
275     *
276     * @param instance1 the first task instance to be compared
277     * @param instance2 the second task instance to be compared
278     *
279     * @return as described
280     *
[2218]281     * @throws IllegalStateException in the case, the object is not correctly initialized
[1294]282     */
283    public TaskEquality compare(ITaskInstance instance1, ITaskInstance instance2)
284        throws IllegalStateException
285    {
286        if (mRuleIndex == null) {
287            throw new IllegalStateException("not initialized");
288        }
289       
290        // LOG.info("checking for equality of " + instance1 + " and " + instance2);
291        TaskEquality instanceEquality = null;
292
293        for (TaskComparisonRule rule : mRuleIndex) {
294            if (rule.isApplicable(instance1, instance2)) {
295                instanceEquality = rule.compare(instance1, instance2);
296                if (instanceEquality != null) {
297                    // LOG.warning("used rule " + rule + " for equality check");
298                    return instanceEquality;
299                }
300            }
301        }
302
303        // LOG.warning("no rule could be applied --> handling tasks as unequal");
304
305        return TaskEquality.UNEQUAL;
306    }
307
308    /**
309     * <p>
310     * this method compares two task instances with respect to the given equality level and returns
311     * true, if this level is given.
312     * </p>
313     *
314     * @param instance1     the first task instance to be compared
315     * @param instance2     the second task instance to be compared
316     * @param equalityLevel the level of equality to be checked for
317     *
318     * @return as described
319     *
[2218]320     * @throws IllegalStateException in the case, the object is not correctly initialized
[1294]321     */
322    public boolean areAtLeastEqual(ITaskInstance        instance1,
323                                   ITaskInstance        instance2,
324                                   TaskEquality equalityLevel)
325    {
326        if (equalityLevel == null) {
327            throw new IllegalArgumentException("required equality level must not be null");
328        }
329       
330        switch (equalityLevel) {
331            case IDENTICAL:
332                return areIdentical(instance1, instance2);
333            case LEXICALLY_EQUAL:
334                return areLexicallyEqual(instance1, instance2);
335            case SYNTACTICALLY_EQUAL:
336                return areSyntacticallyEqual(instance1, instance2);
337            case SEMANTICALLY_EQUAL:
338                return areSemanticallyEqual(instance1, instance2);
339            case UNEQUAL:
340                return !areSemanticallyEqual(instance1, instance2);
341            default:
342                throw new IllegalArgumentException("unknown required equality: " + equalityLevel);
343        }
344    }
345
346    /**
347     * <p>
348     * this method checks if the two given task instances are identical. For this, it iterates its
349     * internal comparison rules. If the first rule returns true, than this method returns true
350     * as well. If no rule returns true, this method returns false.
351     * </p>
352     *
353     * @param instance1 the first task instance to be compared
354     * @param instance2 the second task instance to be compared
355     *
356     * @return as described
357     *
[2218]358     * @throws IllegalStateException in the case, the object is not correctly initialized
[1294]359     */
360    public boolean areIdentical(ITaskInstance instance1, ITaskInstance instance2) {
361        if (mRuleIndex == null) {
362            throw new IllegalStateException("not initialized");
363        }
364       
365        for (TaskComparisonRule rule : mRuleIndex) {
366            if (rule.isApplicable(instance1, instance2) &&
367                rule.areLexicallyEqual(instance1, instance2))
368            {
369                return true;
370            }
371        }
372
373        return false;
374    }
375
376    /**
377     * <p>
378     * this method checks if the two given task instances are lexically equal. For this, it
379     * iterates its internal comparison rules. If the first rule returns true, than this method
380     * returns true, as well. If no rule returns true, this method returns false.
381     * </p>
382     *
383     * @param instance1 the first task instance to be compared
384     * @param instance2 the second task instance to be compared
385     *
386     * @return as described
387     *
[2218]388     * @throws IllegalStateException in the case, the object is not correctly initialized
[1294]389     */
390    public boolean areLexicallyEqual(ITaskInstance instance1, ITaskInstance instance2) {
391        if (mRuleIndex == null) {
392            throw new IllegalStateException("not initialized");
393        }
394       
395        for (TaskComparisonRule rule : mRuleIndex) {
396            if (rule.isApplicable(instance1, instance2) &&
397                rule.areLexicallyEqual(instance1, instance2))
398            {
399                return true;
400            }
401        }
402
403        return false;
404    }
405
406    /**
407     * <p>
408     * this method checks if the two given task instances are syntactically equal. For this, it
409     * iterates its internal comparison rules. If the first rule returns true, than this method
410     * returns true, as well. If no rule returns true, this method returns false.
411     * </p>
412     *
413     * @param instance1 the first task instance to be compared
414     * @param instance2 the second task instance to be compared
415     *
416     * @return as described
417     *
[2218]418     * @throws IllegalStateException in the case, the object is not correctly initialized
[1294]419     */
420    public boolean areSyntacticallyEqual(ITaskInstance instance1, ITaskInstance instance2) {
421        if (mRuleIndex == null) {
422            throw new IllegalStateException("not initialized");
423        }
424       
425        for (TaskComparisonRule rule : mRuleIndex) {
426            if (rule.isApplicable(instance1, instance2) &&
427                rule.areSyntacticallyEqual(instance1, instance2))
428            {
429                return true;
430            }
431        }
432
433        return false;
434    }
435
436    /**
437     * <p>
438     * this method checks if the two given task instances are semantically equal. For this, it
439     * iterates its internal comparison rules. If the first rule returns true, than this method
440     * returns true, as well. If no rule returns true, this method returns false.
441     * </p>
442     *
443     * @param instance1 the first task instance to be compared
444     * @param instance2 the second task instance to be compared
445     *
446     * @return as described
447     *
[2218]448     * @throws IllegalStateException in the case, the object is not correctly initialized
[1294]449     */
450    public boolean areSemanticallyEqual(ITaskInstance instance1, ITaskInstance instance2) {
451        if (mRuleIndex == null) {
452            throw new IllegalStateException("not initialized");
453        }
454       
455        for (TaskComparisonRule rule : mRuleIndex) {
456            if (rule.isApplicable(instance1, instance2) &&
457                rule.areSemanticallyEqual(instance1, instance2))
458            {
459                 return true;
460            }
461        }
462
463        return false;
464    }
465
[439]466}
Note: See TracBrowser for help on using the repository browser.