001 /**
002 * Copyright (C) 2007-2011, Jens Lehmann
003 *
004 * This file is part of DL-Learner.
005 *
006 * DL-Learner is free software; you can redistribute it and/or modify
007 * it under the terms of the GNU General Public License as published by
008 * the Free Software Foundation; either version 3 of the License, or
009 * (at your option) any later version.
010 *
011 * DL-Learner is distributed in the hope that it will be useful,
012 * but WITHOUT ANY WARRANTY; without even the implied warranty of
013 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
014 * GNU General Public License for more details.
015 *
016 * You should have received a copy of the GNU General Public License
017 * along with this program. If not, see <http://www.gnu.org/licenses/>.
018 */
019
020 package org.dllearner.algorithms.refinement;
021
022 import org.dllearner.utilities.owl.ConceptComparator;
023
024 public class NodeComparator implements Heuristic {
025
026 // Vergleich von Konzepten, falls alle anderen Kriterien fehlschlagen
027 ConceptComparator conceptComparator = new ConceptComparator();
028
029 // implementiert einfach die Definition in der Diplomarbeit
030 public int compare(Node n1, Node n2) {
031
032 // sicherstellen, dass Qualität ausgewertet wurde
033 if(n1.isQualityEvaluated() && n2.isQualityEvaluated() && !n1.isTooWeak() && !n2.isTooWeak()) {
034 if(n1.getCoveredNegativeExamples()<n2.getCoveredNegativeExamples())
035 return 1;
036 else if(n1.getCoveredNegativeExamples()>n2.getCoveredNegativeExamples())
037 return -1;
038 else {
039 //TODO: es wäre geringfügig effizienter die Länge nicht mehrfach zu berechnen
040 // Besser: Länge wird einfach ignoriert und stattdessen horizontal expansion
041 // genommen => das ist günstiger, da so verhindert wird, dass das gleiche
042 // Konzept lange ausgeschlachtet wird, obwohl es ein gleich gutes Element gibt,
043 // was vielleicht nur um 1 länger ist;
044 // => damit trotzdem die jeweils besten gefundenen Elemente ermittelt werden
045 // können (da fällt die horizontal expansion dann natürlich als Kriterium
046 // weg, da die nur während des Algorithmus eine Rolle spielt) wird zusätzlich
047 // ein separator NodeComparator genutzt
048 // if(n1.getConcept().getLength()<n2.getConcept().getLength())
049 // return 1;
050 // else if(n1.getConcept().getLength()>n2.getConcept().getLength())
051 // return -1;
052 // else {
053 if(n1.getHorizontalExpansion()<n2.getHorizontalExpansion())
054 return 1;
055 else if(n1.getHorizontalExpansion()>n2.getHorizontalExpansion())
056 return -1;
057 //else
058 // return 0;
059
060 // Vorsicht: es darf nur 0 zurückgegeben werden, wenn die Konzepte identisch sind,
061 // in dem Fall werden sie vom Algorithmus ignoriert
062 // TODO: hier müsste also gleich eine Vergleichsfunktion für Konzepte in
063 // ordered negation normal form einbringen und hätte damit sofort den redundancy
064 // check erledigt (??) => horizontalExpansion könnte allerdings bei gleichen
065 // Konzepten unterschiedlich sein, also ev. doch keine so gute Idee
066
067 else {
068
069 //if(n1.getConcept().hashCode()<n2.getConcept().hashCode())
070 // return 1;
071 //else if(n1.getConcept().hashCode()>n2.getConcept().hashCode())
072 // return -1;
073
074 // throw new RuntimeException("Current implementation cannot cope with candidate concepts with equal hash codes");
075
076 // TODO: es ist nicht sehr gut nur Strings zu vergleichen
077 // int test = n1.getConcept().toString().compareTo(n2.getConcept().toString());
078 return conceptComparator.compare(n1.getConcept(), n2.getConcept());
079 //if(test>0)
080 // return 1;
081 //else if(test<0)
082 // return -1;
083
084 // dieser Fall sollte eigentlich nicht eintreten, auÃer wenn
085 // node entfernt wird => das ist notwendig, wenn horiz. exp.
086 // eines Knotens geändert wird; der muss dann gelöscht und
087 // wieder eingefügt werden
088
089 // System.out.println("equal nodes:");
090 // System.out.println(n1 + " chain: " + n1.getRefinementChainString());
091 // System.out.println(n2 + " chain: " + n2.getRefinementChainString());
092
093 // throw new RuntimeException("same node twice");
094 // return 0;
095 // Absicherung das keine gleichen Konzepte vorkommen
096 // throw new RuntimeException("Current implementation cannot cope with concepts with equal string representations.");
097 }
098
099
100 //}
101 }
102 }
103
104 throw new RuntimeException("Cannot compare nodes, which have no evaluated quality or are too weak.");
105 }
106
107
108 // alle NodeComparators führen zur gleichen Ordnung
109 @Override
110 public boolean equals(Object o) {
111 return (o instanceof NodeComparator);
112 }
113
114 }