/** * Constructs this comparator. * * @param what what to compare * @param with with what * @param deep whether to compare not only the structure of graphs but also graph attributes */ public Test_LearnerComparator(Learner what, Learner with, boolean deep) { super(what); whatToCompareWith = with; compareInDepth = deep; what.setTopLevelListener(this); with.setTopLevelListener(this); }
@Override public boolean AddConstraints( LearnerGraph graph, LearnerGraph outcome, StringBuffer counterExampleHolder) { LearnerGraph copyOfOutcome = null; boolean result = false; // First, we call the expected method if (Thread.currentThread() == secondThread) { result = whatToCompareWith.AddConstraints(graph, outcome, counterExampleHolder); copyOfOutcome = new LearnerGraph(outcome, outcome.config); cGraph = copyOfOutcome; cResult = result; } else { result = decoratedLearner.AddConstraints(graph, outcome, counterExampleHolder); copyOfOutcome = new LearnerGraph(outcome, outcome.config); } syncOnCallOf(KIND_OF_METHOD.M_ADDCONSTRAINTS); if (Thread.currentThread() != secondThread) { // second thread, checking. if (!cResult.equals(new Boolean(result))) failureCode = new IllegalArgumentException("different success value of AddConstraints"); else { if (result) checkGraphEquality(cGraph, copyOfOutcome); } cGraph = null; cResult = null; // reset stored data } syncOnCallOf(KIND_OF_METHOD.M_METHODEXIT); // aims to stop one of the threads running fast // from the first checkCall and overwriting the stored value before the other // thread had a chance to use it in a comparison. return result; }
/** * Both arguments and the return value are stored by the simulator. * * @param plus value loaded from XML * @param minus value loaded from XML */ @Override public synchronized LearnerGraph init( Collection<List<Label>> plus, Collection<List<Label>> minus) { LearnerGraph result = null, copyOfResult = null; // First, we call the expected method if (Thread.currentThread() == secondThread) { result = whatToCompareWith.init(plus, minus); copyOfResult = new LearnerGraph(result, result.config); iGraph = copyOfResult; } else { result = decoratedLearner.init(plus, minus); copyOfResult = new LearnerGraph(result, result.config); } syncOnCallOf(KIND_OF_METHOD.M_INIT); if (Thread.currentThread() != secondThread) { // second thread, checking. checkGraphEquality(iGraph, copyOfResult); iGraph = null; // reset stored data } syncOnCallOf(KIND_OF_METHOD.M_METHODEXIT); // aims to stop one of the threads running fast // from the first checkCall and overwriting the stored value before the other // thread had a chance to use it in a comparison. return result; }
/** * Called by the simulator. * * @param pair loaded from XML. * @param original estimated value. * @param temp estimated value. * @return loaded from XML. */ @Override public synchronized List<List<Label>> RecomputeQuestions( PairScore pair, LearnerGraph original, LearnerGraph temp) { List<List<Label>> result = null; // First, we call the expected method if (Thread.currentThread() == secondThread) { result = whatToCompareWith.ComputeQuestions(pair, original, temp); MqPair = pair; Mquestions = result; } else result = decoratedLearner.ComputeQuestions(pair, original, temp); syncOnCallOf(KIND_OF_METHOD.M_RECOMPUTEQUESTIONS); if (Thread.currentThread() != secondThread) { // checking, ignoring scores and accept-conditions. if (!MqPair.getQ().equals(pair.getQ()) || !MqPair.getR().equals(pair.getR())) failureCode = new IllegalArgumentException( "different RecomputeQuestions pair " + MqPair + " v.s. " + pair); if (!Mquestions.equals(result)) failureCode = new IllegalArgumentException( "different RecomputeQuestions questions: \n" + Mquestions + "\n v.s.\n" + result); MqPair = null; Mquestions = null; // reset stored data } syncOnCallOf(KIND_OF_METHOD.M_METHODEXIT); // aims to stop one of the threads running fast // from the first checkCall and overwriting the stored value before the other // thread had a chance to use it in a comparison. return result; }
/** * Does nothing in the simulator. * * @param pta is always null in the simulator. * @param ptaKind loaded from XML. * @param sequence loaded from XML. * @param accepted loaded from XML. * @param newColour loaded from XML. */ @Override public synchronized void AugmentPTA( LearnerGraph pta, RestartLearningEnum ptaKind, List<Label> sequence, boolean accepted, JUConstants newColour) { AugmentPTAData data = new AugmentPTAData(ptaKind, sequence, accepted, newColour); // now call the expected method if (Thread.currentThread() == secondThread) { whatToCompareWith.AugmentPTA(pta, ptaKind, sequence, accepted, newColour); augmentData = data; } else decoratedLearner.AugmentPTA(pta, ptaKind, sequence, accepted, newColour); syncOnCallOf(KIND_OF_METHOD.M_AUGMENT); if (Thread.currentThread() != secondThread) { if (!data.equals(augmentData)) // second thread, checking. failureCode = new IllegalArgumentException("different augment PTA values"); augmentData = null; // reset stored data } syncOnCallOf(KIND_OF_METHOD.M_METHODEXIT); // aims to stop one of the threads running fast // from the first checkCall and overwriting the stored value before the other // thread had a chance to use it in a comparison. }
/** * Called by the simulator. * * @param graph estimated graph * @return loaded values from XML. */ @Override public synchronized Stack<PairScore> ChooseStatePairs(LearnerGraph graph) { Stack<PairScore> pairsAndScores = new Stack<PairScore>(); Stack<PairScore> result = null; if (Thread.currentThread() == secondThread) { result = whatToCompareWith.ChooseStatePairs(graph); pairsAndScores.addAll(result); // make sure that we do not depend on // subsequent modification of the stack of pairs (one thread may // outrun another one and make changes to it before another one // had a chance to compare the two stacks). pairs = pairsAndScores; } else { // first graph result = decoratedLearner.ChooseStatePairs(graph); pairsAndScores.addAll(result); } syncOnCallOf(KIND_OF_METHOD.M_CHOOSEPAIRS); if (Thread.currentThread() != secondThread) { // checking. pairsAndScores as well as graph is from the first graph. // pairs is from the second one. // Since accept/reject labelling is not stored in the XML file, we have to compare pairs // discounting accept/reject if (pairs.size() != pairsAndScores.size()) throw new IllegalArgumentException( "different sizes of ChooseStatePairs collections of pairs, \n" + pairs + " v.s. \n" + pairsAndScores); Iterator<PairScore> ps1 = pairsAndScores.iterator(), ps2 = pairs.iterator(); while (ps1.hasNext()) { PairScore p1 = ps1.next(), p2 = ps2.next(); if (!p1.getQ().equals(p2.getQ()) || !p1.getR().equals(p2.getR()) || p1.getScore() != p2.getScore() || p1.getAnotherScore() != p2.getAnotherScore()) throw new IllegalArgumentException( "different ChooseStatePairs pairs, " + p1 + " v.s. " + p2); } pairs = null; // reset stored data } syncOnCallOf(KIND_OF_METHOD.M_METHODEXIT); // aims to stop one of the threads running fast // from the first checkCall and overwriting the stored value before the other // thread had a chance to use it in a comparison. return result; }
/** * Simulated check. * * @param g estimated graph, not loaded from XML. * @param question question loaded from XML or computed by a learner. * @param responseForNoRestart ignored. * @param lengthInHardFacts ignored. * @param options set to null by the simulator. * @return value loaded from XML or computed by the learner. */ @Override public synchronized Pair<Integer, String> CheckWithEndUser( LearnerGraph graph, List<Label> argQuestion, int responseForNoRestart, List<Boolean> acceptedElements, PairScore pairBeingMerged, Object[] options) { Pair<Integer, String> result = null; // First, we call the expected method if (Thread.currentThread() == secondThread) { result = whatToCompareWith.CheckWithEndUser( graph, argQuestion, responseForNoRestart, acceptedElements, pairBeingMerged, options); question = argQuestion; cPair = result; } else result = decoratedLearner.CheckWithEndUser( graph, argQuestion, responseForNoRestart, acceptedElements, pairBeingMerged, options); syncOnCallOf(KIND_OF_METHOD.M_CHECKWITHUSER); if (Thread.currentThread() != secondThread) { // checking. if (!question.equals(argQuestion)) failureCode = new IllegalArgumentException("different CheckWithEndUser questions"); if (!cPair.equals(result)) failureCode = new IllegalArgumentException( "different CheckWithEndUser results " + cPair.firstElem + " v.s. " + result.firstElem + " and " + cPair.secondElem + " v.s. " + result.secondElem); cPair = null; question = null; // reset stored data } syncOnCallOf(KIND_OF_METHOD.M_METHODEXIT); // aims to stop one of the threads running fast // from the first checkCall and overwriting the stored value before the other // thread had a chance to use it in a comparison. return result; }
/** * Does nothing in the simulator. * * @param mode value loaded from XML. */ @Override public synchronized void Restart(RestartLearningEnum mode) { // First, we call the expected method if (Thread.currentThread() == secondThread) { whatToCompareWith.Restart(mode); rMode = mode; } else decoratedLearner.Restart(mode); syncOnCallOf(KIND_OF_METHOD.M_RESTART); if (Thread.currentThread() != secondThread) { // checking. if (!rMode.equals(mode)) failureCode = new IllegalArgumentException("different Restart mode"); rMode = null; // reset stored data } syncOnCallOf(KIND_OF_METHOD.M_METHODEXIT); // aims to stop one of the threads running fast // from the first checkCall and overwriting the stored value before the other // thread had a chance to use it in a comparison. }
/** * Returns the graph stored in XML. * * @param original graph to be processed, the simulator attempts to supply a relevant value, * however it is not certain to be correct. * @param pair the pair to be merged. Loaded from XML file (without scores). * @return graph loaded from XML file. */ @Override public synchronized LearnerGraph MergeAndDeterminize(LearnerGraph original, StatePair pair) { LearnerGraph result = null, copyOfResult = null; // First, we call the expected method if (Thread.currentThread() == secondThread) { result = whatToCompareWith.MergeAndDeterminize(original, pair); copyOfResult = new LearnerGraph( result, result .config); // since a tread which produced result may exit and modify the graph, we // have to take a copy of it. mPair = pair; mGraph = copyOfResult; } else { result = decoratedLearner.MergeAndDeterminize(original, pair); copyOfResult = new LearnerGraph(result, result.config); } syncOnCallOf(KIND_OF_METHOD.M_MERGEANDDETERMINIZE); if (Thread.currentThread() != secondThread) { // checking, considering that acceptance conditions are not stored in // XML. if (!mPair.getQ().equals(pair.getQ()) || !mPair.getR().equals(pair.getR())) failureCode = new IllegalArgumentException( "different MergeAndDeterminize pair " + mPair + " v.s. " + pair); checkGraphEquality(mGraph, copyOfResult); mPair = null; mGraph = null; // reset stored data } syncOnCallOf(KIND_OF_METHOD.M_METHODEXIT); // aims to stop one of the threads running fast // from the first checkCall and overwriting the stored value before the other // thread had a chance to use it in a comparison. return result; }