source: trunk/autoquest-ui-core/src/main/java/de/ugoe/cs/autoquest/commands/usability/CMDgetTaskModelSimilarity.java @ 1895

Last change on this file since 1895 was 1895, checked in by pharms, 9 years ago
  • added support to compare task models with each other
File size: 29.0 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.commands.usability;
16
17import java.text.DecimalFormat;
18import java.util.ArrayList;
19import java.util.Collections;
20import java.util.HashMap;
21import java.util.IdentityHashMap;
22import java.util.LinkedList;
23import java.util.List;
24import java.util.Map;
25import java.util.logging.Level;
26
27import de.ugoe.cs.autoquest.CommandHelpers;
28import de.ugoe.cs.autoquest.eventcore.IEventTarget;
29import de.ugoe.cs.autoquest.tasktrees.taskequality.TaskEquality;
30import de.ugoe.cs.autoquest.tasktrees.taskequality.TaskEqualityRuleManager;
31import de.ugoe.cs.autoquest.tasktrees.temporalrelation.TaskComparator;
32import de.ugoe.cs.autoquest.tasktrees.temporalrelation.utils.SimilarTasks;
33import de.ugoe.cs.autoquest.tasktrees.treeifc.DefaultTaskTraversingVisitor;
34import de.ugoe.cs.autoquest.tasktrees.treeifc.IEventTask;
35import de.ugoe.cs.autoquest.tasktrees.treeifc.IEventTaskInstance;
36import de.ugoe.cs.autoquest.tasktrees.treeifc.ISelection;
37import de.ugoe.cs.autoquest.tasktrees.treeifc.ISequence;
38import de.ugoe.cs.autoquest.tasktrees.treeifc.ITask;
39import de.ugoe.cs.autoquest.tasktrees.treeifc.ITaskModel;
40import de.ugoe.cs.autoquest.tasktrees.treeifc.TaskMetric;
41import de.ugoe.cs.util.StopWatch;
42import de.ugoe.cs.util.console.Command;
43import de.ugoe.cs.util.console.Console;
44import de.ugoe.cs.util.console.GlobalDataContainer;
45
46/**
47 * <p>
48 * compares a set of task models with each other and drops their similarity as results
49 * </p>
50 *
51 * @author Patrick Harms
52 * @version 1.0
53 */
54public class CMDgetTaskModelSimilarity implements Command {
55
56    /*
57     * (non-Javadoc)
58     *
59     * @see de.ugoe.cs.util.console.Command#help()
60     */
61    @Override
62    public String help() {
63        return "getTaskModelSimilarity <tasktree1> <tasktree2> ...";
64    }
65
66    /*
67     * (non-Javadoc)
68     *
69     * @see de.ugoe.cs.util.console.Command#run(java.util.List)
70     */
71    @Override
72    public void run(List<Object> parameters) {
73        List<String> inputTaskTreeNames = new LinkedList<>();
74       
75        try {
76            for (Object param : parameters) {
77                inputTaskTreeNames.add((String) param);
78            }
79        }
80        catch (Exception e) {
81            throw new IllegalArgumentException("must provide valid input task tree names");
82        }
83
84        Map<ITaskModel, List<ISequence>> inputTaskModels = new IdentityHashMap<>();
85       
86        for (String inputTaskTreeName : inputTaskTreeNames) {
87            Object dataObject = GlobalDataContainer.getInstance().getData(inputTaskTreeName);
88            if (dataObject == null) {
89                CommandHelpers.objectNotFoundMessage(inputTaskTreeName);
90                return;
91            }
92            if (!(dataObject instanceof ITaskModel)) {
93                CommandHelpers.objectNotType(inputTaskTreeName, "ITaskModel");
94                return;
95            }
96           
97            List<ISequence> tasksToCompare = new LinkedList<>();
98           
99            for (ITask task : ((ITaskModel) dataObject).getTasks()) {
100                if (task instanceof ISequence) {
101                    tasksToCompare.add((ISequence) task);
102                }
103            }
104           
105            inputTaskModels.put((ITaskModel) dataObject, tasksToCompare);
106        }
107       
108        SimilarityStatistics statistics = new SimilarityStatistics();
109       
110        getTaskModelSimilarity(inputTaskModels, statistics);
111       
112        Console.println("\nsimilarity statistics of all comparisons");
113        statistics.dump();
114    }
115
116    /**
117     *
118     */
119    private void getTaskModelSimilarity(Map<ITaskModel, List<ISequence>> inputTaskModels,
120                                        SimilarityStatistics             statistics)
121    {
122        // create the indexes to not do too many comparisons
123        Map<ITaskModel, Map<Integer, Map<IEventTarget, List<ISequence>>>> index1 =
124            new IdentityHashMap<>();
125       
126        Map<ISequence, Integer> index2 = new HashMap<>();
127        Map<ISequence, IEventTarget> index3 = new HashMap<>();
128       
129        final List<IEventTask> terminalNodes = new ArrayList<>();
130        final List<ISelection> selections = new ArrayList<>();
131       
132        for (Map.Entry<ITaskModel, List<ISequence>> entry : inputTaskModels.entrySet()) {
133            for (ISequence sequence : entry.getValue()) {
134                terminalNodes.clear();
135                selections.clear();
136               
137                sequence.accept(new DefaultTaskTraversingVisitor() {
138                    @Override
139                    public void visit(IEventTask eventTask) {
140                        terminalNodes.add(eventTask);
141                    }
142                    @Override
143                    public void visit(ISelection selection) {
144                        selections.add(selection);
145                        // no need to traverse children as a sequences containing a selection
146                        // will be handled differently
147                    }
148                });
149               
150                int length = terminalNodes.size();
151                IEventTarget firstTarget = ((IEventTaskInstance) terminalNodes.get(0).getInstances()
152                    .iterator().next()).getEvent().getTarget();
153               
154                if (selections.size() > 0) {
155                    length = -1;
156                    firstTarget = null;
157                }
158
159                Map<Integer, Map<IEventTarget, List<ISequence>>> lengthMap =
160                    index1.get(entry.getKey());
161               
162                if (lengthMap == null) {
163                    lengthMap = new HashMap<>();
164                    index1.put(entry.getKey(), lengthMap);
165                }
166               
167                Map<IEventTarget, List<ISequence>> firstTaskMap = lengthMap.get(length);
168               
169                if (firstTaskMap == null) {
170                    firstTaskMap = new HashMap<>();
171                    lengthMap.put(length, firstTaskMap);
172                }
173               
174                List<ISequence> compareList = firstTaskMap.get(firstTarget);
175               
176                if (compareList == null) {
177                    compareList = new LinkedList<ISequence>();
178                    firstTaskMap.put(firstTarget, compareList);
179                }
180               
181                compareList.add(sequence);
182                index2.put(sequence, length);
183                index3.put(sequence, firstTarget);
184            }
185        }
186       
187        // create the comparison runnables
188        List<ComparisonRunnable> runnables = new LinkedList<>();
189       
190        for (Map.Entry<ITaskModel, List<ISequence>> model1 : inputTaskModels.entrySet()) {
191            for (Map.Entry<ITaskModel, List<ISequence>> model2 : inputTaskModels.entrySet()) {
192                if (model1.getKey() != model2.getKey()) {
193                    runnables.add(new ComparisonRunnable(model1.getKey(), model1.getValue(),
194                                                         model2.getKey(), model2.getValue(),
195                                                         Collections.unmodifiableMap
196                                                             (index1.get(model2.getKey())),
197                                                         Collections.unmodifiableMap(index2),
198                                                         Collections.unmodifiableMap(index3),
199                                                         runnables));
200                }
201            }
202        }
203       
204        // execute the threads
205        Console.traceln(Level.FINE, "scheduling " + runnables.size() + " comparison threads");
206       
207        synchronized (runnables) {
208            int startedRunnables = 0;
209            for (ComparisonRunnable runnable : runnables) {
210                while (startedRunnables >= Math.max(1, Runtime.getRuntime().availableProcessors()))
211                {
212                    try {
213                        Console.traceln(Level.FINER, "waiting for next thread to finish");
214                        runnables.wait();
215                        startedRunnables--;
216                        Console.traceln(Level.FINER, "thread finished");
217                    }
218                    catch (InterruptedException e) {
219                        // should not happen
220                        Console.logException(e);
221                    }
222                }
223           
224                Console.traceln(Level.FINER, "starting next thread");
225                startedRunnables++;
226                Console.traceln(Level.FINE, "comparing " + runnable.tasks1.size()
227                                + " tasks of model " + runnable.model1 + " with " +
228                                runnable.tasks2.size() + " tasks of model " + runnable.model2);
229             
230                new Thread(runnable).start();
231                Console.traceln(Level.FINER, "started next thread " + runnable);
232            }
233           
234            while (startedRunnables > 0) {
235                try {
236                    Console.traceln(Level.FINER, "waiting for next thread to finish");
237                    runnables.wait();
238                    startedRunnables--;
239                    Console.traceln(Level.FINER, "thread finished");
240                }
241                catch (InterruptedException e) {
242                    // should not happen
243                    Console.logException(e);
244                }
245            }
246        }
247
248        // merge the results
249        Console.traceln(Level.FINER, "all threads finished, mergin results");
250       
251        for (ComparisonRunnable runnable : runnables) {
252            Console.println("\n similarity statistics of comparison between " + runnable.model1 +
253                            " and " + runnable.model2);
254            runnable.getStatistics().dump();
255            statistics.mergeWith(runnable.getStatistics());
256        }
257    }
258
259    /**
260     *
261     */
262    private static class SimilarityStatistics {
263       
264        /**  */
265        private int taskCounter = 0;
266       
267        /** */
268        private int maxCoverage = 0;
269       
270        /**  */
271        private Map<Integer, Integer> coverageCounters = new HashMap<>();
272       
273        /**  */
274        private Map<Integer, Map<Integer, Map<TaskEquality, Integer>>> equalityCounters =
275            new HashMap<>();
276       
277        /**
278         *
279         */
280        private void store(ITask        task,
281                           ITaskModel   model,
282                           ITask        other,
283                           ITaskModel   otherModel,
284                           TaskEquality equality)
285        {
286            int coverageRatio1 =
287                model.getTaskInfo(task).getMeasureValue(TaskMetric.EVENT_COVERAGE);
288            int coverageRatio2 =
289                otherModel.getTaskInfo(other).getMeasureValue(TaskMetric.EVENT_COVERAGE);
290           
291            addToMaps(coverageRatio1, 1);
292            addToMaps(coverageRatio1, coverageRatio2, equality, 1);
293            taskCounter++;
294            maxCoverage = Math.max(maxCoverage, coverageRatio1);
295        }
296       
297        /**
298         *
299         */
300        private void store(ITask task, ITaskModel model) {
301            int coverageRatio1 =
302                model.getTaskInfo(task).getMeasureValue(TaskMetric.EVENT_COVERAGE);
303           
304            addToMaps(coverageRatio1, 1);
305            addToMaps(coverageRatio1, 0, TaskEquality.UNEQUAL, 1);
306            taskCounter++;
307            maxCoverage = Math.max(maxCoverage, coverageRatio1);
308        }
309
310        /**
311         *
312         */
313        private void mergeWith(SimilarityStatistics statistics) {
314            for (Map.Entry<Integer, Map<Integer, Map<TaskEquality, Integer>>> entry1 :
315                     statistics.equalityCounters.entrySet())
316            {
317                for (Map.Entry<Integer, Map<TaskEquality, Integer>> entry2 :
318                         entry1.getValue().entrySet())
319                {
320                    for (Map.Entry<TaskEquality, Integer> entry3 : entry2.getValue().entrySet()) {
321                        addToMaps
322                            (entry1.getKey(), entry2.getKey(), entry3.getKey(), entry3.getValue());
323                    }
324                }
325            }
326           
327            for (Map.Entry<Integer, Integer> entry : statistics.coverageCounters.entrySet()) {
328                addToMaps(entry.getKey(), entry.getValue());
329            }
330           
331            taskCounter += statistics.taskCounter;
332            maxCoverage = Math.max(maxCoverage, statistics.taskCounter);
333        }
334
335        /**
336         *
337         */
338        private void addToMaps(int ratio, int increment) {
339            Integer counter = coverageCounters.get(ratio);
340
341            if (counter == null) {
342                coverageCounters.put(ratio, increment);
343            }
344            else {
345                coverageCounters.put(ratio, counter + increment);
346            }
347        }
348       
349        /**
350         *
351         */
352        private void addToMaps(Integer ratio1, Integer ratio2, TaskEquality equality, int value) {
353            Map<Integer, Map<TaskEquality, Integer>> counters1 = equalityCounters.get(ratio1);
354               
355            if (counters1 == null) {
356                counters1 = new HashMap<>();
357                equalityCounters.put(ratio1, counters1);
358            }
359
360            Map<TaskEquality, Integer> counters2 = counters1.get(ratio2);
361
362            if (counters2 == null) {
363                counters2 = new HashMap<>();
364                counters1.put(ratio2, counters2);
365            }
366
367            Integer counter = counters2.get(equality);
368
369            if (counter == null) {
370                counters2.put(equality, value);
371            }
372            else {
373                counters2.put(equality, counter + value);
374            }
375        }
376
377        /**
378         *
379         */
380        private void dump() {
381            Console.println("Statistics of Similarity");
382            Console.println("========================");
383           
384            int[][] bins = getBinsOfAlmostEqualSize();
385            int lowerBorder1;
386            int higherBorder1;
387            int lowerBorder2;
388            int higherBorder2;
389            int allEqualitiesOfBin = 0;
390            int allEqualities = 0;
391           
392            for (int i = bins.length - 1; i >= 0 ; i--) {
393                if (i <= 0) {
394                    lowerBorder1 = 0;
395                }
396                else {
397                    lowerBorder1 = bins[i - 1][0] + 1;
398                }
399               
400                higherBorder1 = bins[i][0];
401               
402                allEqualitiesOfBin = 0;
403               
404                Console.println("similarities of " + bins[i][1] + " tasks with " + lowerBorder1 +
405                                " to " + higherBorder1 + "‰ coverage");
406               
407                for (int j = bins.length - 1; j >= 0; j--) {
408                    if (j <= 0) {
409                        lowerBorder2 = 0;
410                    }
411                    else {
412                        lowerBorder2 = bins[j - 1][0] + 1;
413                    }
414                   
415                    higherBorder2 = bins[j][0];
416
417                    Console.print("  --> to " + bins[j][1] + " tasks with " + lowerBorder2 +
418                                  " to " + higherBorder2 + "‰ coverage");
419                   
420                    Console.print("    | ");
421                    int allInBin = countAllInBin(lowerBorder1, higherBorder1);
422
423                    int count1 = countEqualities(lowerBorder1, higherBorder1, lowerBorder2,
424                                                 higherBorder2, TaskEquality.LEXICALLY_EQUAL);
425                   
426                    dump(count1, allInBin, "LEX");
427                    Console.print("\t| ");
428
429                    int count2 = countEqualities(lowerBorder1, higherBorder1, lowerBorder2,
430                                                 higherBorder2, TaskEquality.SYNTACTICALLY_EQUAL);
431
432                    dump(count2, allInBin, "SYN");
433                    Console.print("\t| ");
434
435                    int count3 = countEqualities(lowerBorder1, higherBorder1, lowerBorder2,
436                                                 higherBorder2, TaskEquality.SEMANTICALLY_EQUAL);
437                   
438                    dump(count3, allInBin, "SEM");
439                    Console.print("\t|| ");
440
441                    int count4 = countEqualities(lowerBorder1, higherBorder1, lowerBorder2,
442                                                 higherBorder2, null);
443                   
444                    dump(count4, allInBin, "SIM");
445                    Console.print("\t|| ");
446
447                    dump(count1 + count2 + count3 + count4, allInBin, "ALL");
448                    Console.println("");
449                   
450                    allEqualitiesOfBin += count1 + count2 + count3 + count4;
451                }
452               
453                Console.print("  --> to all other tasks\t");
454                dump(allEqualitiesOfBin, taskCounter, "ALL");
455                Console.println("");
456               
457                allEqualities += allEqualitiesOfBin;
458            }
459           
460            Console.println("");
461            Console.print("complete recall is ");
462            dump(allEqualities, taskCounter, "ALL");
463            Console.println("");
464        }
465
466        /**
467         *
468         */
469        private int[][] getBinsOfAlmostEqualSize() {
470            int[][] result = new int[5][];
471           
472            for (int i = 0; i < result.length; i++) {
473                result[i] = new int[2];
474            }
475           
476            int averageBinSize = taskCounter / result.length;
477            int aimedBinSize = averageBinSize;
478           
479            int index = 0;
480           
481            for (int i = 0; i < maxCoverage; i++) {
482                if (result[index][1] > aimedBinSize) {
483                    // try to compensate, if the previous bin was a little too large
484                    aimedBinSize = averageBinSize + averageBinSize - result[index][1];
485                    index++;
486                }
487
488                Integer value = coverageCounters.get(i);
489               
490                if (value != null) {
491                    result[index][0] = i;
492                    result[index][1] += value;
493                }
494            }
495           
496            return result;
497        }
498
499        /**
500         *
501         */
502        private void dump(int noOfEqualTasks, int noOfAllTasks, String prefix) {
503            Console.print(prefix);
504            Console.print("\t: ");
505
506            if (noOfAllTasks > 0) {
507                double value = ((double) (noOfEqualTasks * 100)) / noOfAllTasks;
508                Console.print(noOfEqualTasks + " (");
509                Console.print(new DecimalFormat("###.#").format(value));
510                Console.print("%)");
511            }
512            else {
513                Console.print("n.a.");
514            }
515        }
516
517        /**
518         *
519         */
520        private int countEqualities(int          lowerBorder1,
521                                    int          higherBorder1,
522                                    int          lowerBorder2,
523                                    int          higherBorder2,
524                                    TaskEquality equality)
525        {
526            int counter = 0;
527           
528            for (int i = lowerBorder1; i <= higherBorder1; i++) {
529                Map<Integer, Map<TaskEquality, Integer>> counters1 = equalityCounters.get(i);
530
531                if (counters1 != null) {
532                    for (int j = lowerBorder2; j <= higherBorder2; j++) {
533                        Map<TaskEquality, Integer> counters2 = counters1.get(j);
534               
535                        if (counters2 != null) {
536                            Integer counterObj = counters2.get(equality);
537                   
538                            if (counterObj != null) {
539                                counter += counterObj;
540                            }
541                        }
542                    }
543                }
544            }
545           
546            return counter;
547        }
548
549        /**
550         *
551         */
552        private int countAllInBin(int lowerBorder1, int higherBorder1) {
553            int coverageCounter = 0;
554           
555            for (int i = lowerBorder1; i <= higherBorder1; i++) {
556                Integer value = coverageCounters.get(i);
557               
558                if (value != null) {
559                    coverageCounter += value;
560                }
561            }
562           
563            return coverageCounter;
564        }
565    }
566
567    /**
568     *
569     */
570    private static class ComparisonRunnable implements Runnable {
571       
572        /** */
573        private ITaskModel model1;
574       
575        /** */
576        private ITaskModel model2;
577       
578        /** */
579        private List<ISequence> tasks1;
580       
581        /** */
582        private List<ISequence> tasks2;
583       
584        /** */
585        private Map<Integer, Map<IEventTarget, List<ISequence>>> lengthIndex1;
586       
587        /** */
588        private Map<ISequence, Integer> lengthIndex2;
589       
590        /** */
591        private Map<ISequence, IEventTarget> firstTargetIndex;
592
593        /** */
594        private Object semaphore;
595       
596        /** */
597        private SimilarityStatistics statistics = new SimilarityStatistics();
598       
599        /**
600         *
601         */
602        private ComparisonRunnable(ITaskModel                                       model1,
603                                   List<ISequence>                                  tasks1,
604                                   ITaskModel                                       model2,
605                                   List<ISequence>                                  tasks2,
606                                   Map<Integer, Map<IEventTarget, List<ISequence>>> lengthIndex1,
607                                   Map<ISequence, Integer>                          lengthIndex2,
608                                   Map<ISequence, IEventTarget>                     firstTargetIndex,
609                                   Object                                           semaphore)
610        {
611            this.model1 = model1;
612            this.tasks1 = tasks1;
613            this.model2 = model2;
614            this.tasks2 = tasks2;
615            this.lengthIndex1 = lengthIndex1;
616            this.lengthIndex2 = lengthIndex2;
617            this.firstTargetIndex = firstTargetIndex;
618            this.semaphore = semaphore;
619        }
620
621        /* (non-Javadoc)
622         * @see java.lang.Runnable#run()
623         */
624        @Override
625        public void run() {
626            TaskEqualityRuleManager equalityRuleManager = TaskEqualityRuleManager.getInstance();
627            TaskComparator comparator = new TaskComparator(TaskEquality.SEMANTICALLY_EQUAL);
628            TaskEquality mostCommonEquality;
629            ITask mostSimilarTask;
630            TaskEquality equality;
631            SimilarTasks similarity;
632
633            List<ISequence> tasksToCompareWith = new ArrayList<ISequence>();
634            StopWatch watch = new StopWatch();
635            watch.start("all comparisons ");
636            int count = 0;
637            for (ISequence task : tasks1) {
638                int length = lengthIndex2.get(task);
639                IEventTarget firstTarget = firstTargetIndex.get(task);
640                tasksToCompareWith.clear();
641               
642                // add tasks with same length
643                Map<IEventTarget, List<ISequence>> eventTaskMap = lengthIndex1.get(length);
644                List<ISequence> toCompare;
645               
646                if (eventTaskMap != null) {
647                    toCompare = eventTaskMap.get(firstTarget);
648               
649                    if (toCompare != null) {
650                        tasksToCompareWith.addAll(toCompare);
651                    }
652                }
653               
654                // add tasks containing selections
655                eventTaskMap = lengthIndex1.get(-1);
656               
657                if (eventTaskMap != null) {
658                    toCompare = eventTaskMap.get(firstTarget);
659               
660                    if (toCompare != null) {
661                        tasksToCompareWith.addAll(toCompare);
662                    }
663                }
664               
665                mostCommonEquality = null;
666                mostSimilarTask = null;
667               
668                for (ITask taskToCompare : tasksToCompareWith) {
669                    count++;
670                    watch.start("normal comparison");
671                    equality = equalityRuleManager.compare(task, taskToCompare);
672                    watch.stop("normal comparison");
673                   
674                    if ((equality != TaskEquality.UNEQUAL) &&
675                        ((mostCommonEquality == null) || (equality.isAtLeast(mostCommonEquality))))
676                    {
677                        // >>>>>>>>>>>>>>>>>>>>>> TEST IMPLEMENTATION >>>>>>>>>>>>>>>>>>>>>>>>>>>
678                        // synchronized (System.out) {
679                        //     System.out.println("found equal tasks: " + equality);
680                        //     new TaskTreeEncoder().encode(task, System.out);
681                        //     new TaskTreeEncoder().encode(taskToCompare, System.out);
682                        // }
683                        // <<<<<<<<<<<<<<<<<<<<<< TEST IMPLEMENTATION <<<<<<<<<<<<<<<<<<<<<<<<<<<
684
685                        mostCommonEquality = equality;
686                        mostSimilarTask = taskToCompare;
687                       
688                        if (mostCommonEquality.isAtLeast(TaskEquality.LEXICALLY_EQUAL)) {
689                            // we found a lexically equal match, the most concrete that
690                            // we can find. We can break up here
691                            break;
692                        }
693                    }
694                }
695               
696                if (mostCommonEquality != null) {
697                    statistics.store(task, model1, mostSimilarTask, model2, mostCommonEquality);
698                }
699                else {
700                    int lowestDiffLevel = Integer.MAX_VALUE;
701                    for (ITask taskToCompare : tasksToCompareWith) {
702                        count++;
703                        watch.start("similarity comparison");
704                        similarity = SimilarTasks.compareTasks(task, taskToCompare, comparator);
705                        watch.stop("similarity comparison");
706                       
707                        if (similarity.getDiffLevel() < lowestDiffLevel) {
708                            lowestDiffLevel = similarity.getDiffLevel();
709                            mostSimilarTask = taskToCompare;
710                           
711                            if (lowestDiffLevel <= 0) {
712                                // >>>>>>>>>>>>>>>>>>>>>> TEST IMPLEMENTATION >>>>>>>>>>>>>>>>>>>>>
713                                // synchronized (System.out) {
714                                //     System.out.println("found similar tasks");
715                                //     similarity.dump(System.out);
716                                // }
717                                // <<<<<<<<<<<<<<<<<<<<<< TEST IMPLEMENTATION <<<<<<<<<<<<<<<<<<<<<
718
719                                // we found a fully similar task. We will not find any more
720                                // similar, hence we break
721                                break;
722                            }
723                        }
724                    }
725                   
726                    if (lowestDiffLevel <= 0) {
727                        statistics.store(task, model1, mostSimilarTask, model2, null);
728                    }
729                    else {
730                        statistics.store(task, model1);
731                    }
732                }
733            }
734           
735            System.out.println("performed " + count + " comparisons");
736           
737            watch.stop("all comparisons ");
738            watch.dumpStatistics(System.out);
739           
740            synchronized (semaphore) {
741                semaphore.notify();
742            }
743        }
744
745        /**
746         * @return the statistics
747         */
748        private SimilarityStatistics getStatistics() {
749            return statistics;
750        }
751       
752    }
753}
Note: See TracBrowser for help on using the repository browser.