From 8c04e4d8003f33848ee84011f8427fe92d55001f Mon Sep 17 00:00:00 2001 From: RncLsn Date: Fri, 5 Jun 2015 12:22:31 +0100 Subject: Violation statistics. --- .../pagoda/multistage/MultiStageQueryEngine.java | 43 +++++++++++++++++++++- .../ac/ox/cs/pagoda/reasoner/MyQueryReasoner.java | 4 +- .../pagoda/reasoner/light/RDFoxAnswerTuples.java | 17 +++++++++ .../rules/approximators/SkolemTermsManager.java | 7 ++++ src/uk/ac/ox/cs/pagoda/util/PagodaProperties.java | 26 ++++++++++++- .../ox/cs/pagoda/util/disposable/Disposable.java | 9 ----- 6 files changed, 94 insertions(+), 12 deletions(-) (limited to 'src/uk/ac/ox/cs') diff --git a/src/uk/ac/ox/cs/pagoda/multistage/MultiStageQueryEngine.java b/src/uk/ac/ox/cs/pagoda/multistage/MultiStageQueryEngine.java index af1b413..479905d 100644 --- a/src/uk/ac/ox/cs/pagoda/multistage/MultiStageQueryEngine.java +++ b/src/uk/ac/ox/cs/pagoda/multistage/MultiStageQueryEngine.java @@ -1,5 +1,6 @@ package uk.ac.ox.cs.pagoda.multistage; +import org.semanticweb.HermiT.model.DLClause; import uk.ac.ox.cs.JRDFox.JRDFStoreException; import uk.ac.ox.cs.pagoda.constraints.BottomStrategy; import uk.ac.ox.cs.pagoda.multistage.treatement.Pick4NegativeConceptNaive; @@ -9,14 +10,26 @@ import uk.ac.ox.cs.pagoda.query.GapByStore4ID; import uk.ac.ox.cs.pagoda.query.QueryRecord; import uk.ac.ox.cs.pagoda.rules.DatalogProgram; import uk.ac.ox.cs.pagoda.rules.Program; +import uk.ac.ox.cs.pagoda.util.PagodaProperties; import uk.ac.ox.cs.pagoda.util.Timer; import uk.ac.ox.cs.pagoda.util.Utility; import uk.ac.ox.cs.pagoda.util.disposable.DisposedException; +import java.io.BufferedWriter; +import java.io.IOException; +import java.nio.file.Files; +import java.nio.file.Path; +import java.nio.file.Paths; +import java.util.ArrayList; import java.util.Collection; +import java.util.HashMap; +import java.util.List; +import java.util.stream.Collectors; public class MultiStageQueryEngine extends StageQueryEngine { + private HashMap statistics = new HashMap<>(); + public MultiStageQueryEngine(String name, boolean checkValidity) { super(name, checkValidity); } @@ -94,6 +107,14 @@ public class MultiStageQueryEngine extends StageQueryEngine { return ret; } + @Override + public void dispose() { + super.dispose(); + + if(PagodaProperties.isDebuggingMode()) + outputStatistics(); + } + private int materialise(MultiStageUpperProgram program, Treatment treatment, GapByStore4ID gap) { if(gap != null) treatment.addAdditionalGapTuples(); @@ -169,7 +190,11 @@ public class MultiStageQueryEngine extends StageQueryEngine { subTimer.reset(); oldTripleCount = store.getTriplesCount(); - Utility.logInfo("Number of violations: " + violations.size()); + Utility.logDebug("Number of violations: " + violations.size()); + + updateStatistics("violationClauses", violations.stream() + .map(Violation::getClause) + .collect(Collectors.toList())); for(Violation v : violations) { @@ -198,5 +223,21 @@ public class MultiStageQueryEngine extends StageQueryEngine { return 0; } + private void updateStatistics(String key, List value) { + if(!statistics.containsKey(key)) + statistics.put(key, new ArrayList()); + statistics.get(key).add(value.stream().map(DLClause::toString).collect(Collectors.toList())); + } + + private void outputStatistics() { + Path statisticsPath = PagodaProperties.getDefaultStatisticsDir() + .resolve(Paths.get("MultiStageQueryEngine-ViolationSequence.json")); + try(BufferedWriter writer = Files.newBufferedWriter(statisticsPath)) { + QueryRecord.GsonCreator.getInstance().toJson(statistics, writer); + } catch(IOException e) { + e.printStackTrace(); + } + } + } diff --git a/src/uk/ac/ox/cs/pagoda/reasoner/MyQueryReasoner.java b/src/uk/ac/ox/cs/pagoda/reasoner/MyQueryReasoner.java index 727f80d..e6e508a 100644 --- a/src/uk/ac/ox/cs/pagoda/reasoner/MyQueryReasoner.java +++ b/src/uk/ac/ox/cs/pagoda/reasoner/MyQueryReasoner.java @@ -370,7 +370,7 @@ class MyQueryReasoner extends QueryReasoner { relevantStore.importDataFromABoxOf(relevantSubset); - int queryDependentMaxTermDepth = 1; // TODO make it dynamic + int queryDependentMaxTermDepth = 5; // TODO make it dynamic int materialisationTag = relevantStore.materialiseSkolemly(relevantProgram, null, queryDependentMaxTermDepth); queryRecord.addProcessingTime(Step.SKOLEM_UPPER_BOUND, t.duration()); @@ -386,6 +386,8 @@ class MyQueryReasoner extends QueryReasoner { boolean isFullyProcessed = queryUpperStore(relevantStore, queryRecord, queryRecord.getExtendedQueryText(), Step.SKOLEM_UPPER_BOUND); + + relevantStore.dispose(); Utility.logInfo("Semi-Skolemised relevant upper store has been evaluated"); return isFullyProcessed; } diff --git a/src/uk/ac/ox/cs/pagoda/reasoner/light/RDFoxAnswerTuples.java b/src/uk/ac/ox/cs/pagoda/reasoner/light/RDFoxAnswerTuples.java index 1e8181f..f823232 100644 --- a/src/uk/ac/ox/cs/pagoda/reasoner/light/RDFoxAnswerTuples.java +++ b/src/uk/ac/ox/cs/pagoda/reasoner/light/RDFoxAnswerTuples.java @@ -9,6 +9,7 @@ import uk.ac.ox.cs.JRDFox.store.TupleIterator; import uk.ac.ox.cs.pagoda.query.AnswerTuple; import uk.ac.ox.cs.pagoda.query.AnswerTuples; import uk.ac.ox.cs.pagoda.util.Utility; +import uk.ac.ox.cs.pagoda.util.disposable.DisposedException; public class RDFoxAnswerTuples extends AnswerTuples { @@ -35,11 +36,15 @@ public class RDFoxAnswerTuples extends AnswerTuples { @Override public boolean isValid() { + if(isDisposed()) throw new DisposedException(); + return multi != 0; } @Override public int getArity() { + if(isDisposed()) throw new DisposedException(); + try { return m_iter.getArity(); } catch (JRDFStoreException e) { @@ -50,6 +55,8 @@ public class RDFoxAnswerTuples extends AnswerTuples { @Override public void moveNext() { + if(isDisposed()) throw new DisposedException(); + try { multi = m_iter.getNext(); } catch (JRDFStoreException e) { @@ -65,11 +72,15 @@ public class RDFoxAnswerTuples extends AnswerTuples { @Override public AnswerTuple getTuple() { + if(isDisposed()) throw new DisposedException(); + return new AnswerTuple(m_iter, m_answerVars.length); } @Override public void reset() { + if(isDisposed()) throw new DisposedException(); + try { multi = m_iter.open(); } catch (JRDFStoreException e) { @@ -79,17 +90,23 @@ public class RDFoxAnswerTuples extends AnswerTuples { @Override public boolean contains(AnswerTuple t) { + if(isDisposed()) throw new DisposedException(); + Utility.logError("Unsupported operation in RDFoxAnswerTuples"); return false; } @Override public void remove() { + if(isDisposed()) throw new DisposedException(); + Utility.logError("Unsupported operation in RDFoxAnswerTuples"); } @Override public String[] getAnswerVariables() { + if(isDisposed()) throw new DisposedException(); + return m_answerVars; } diff --git a/src/uk/ac/ox/cs/pagoda/rules/approximators/SkolemTermsManager.java b/src/uk/ac/ox/cs/pagoda/rules/approximators/SkolemTermsManager.java index ef004c4..44daf7a 100644 --- a/src/uk/ac/ox/cs/pagoda/rules/approximators/SkolemTermsManager.java +++ b/src/uk/ac/ox/cs/pagoda/rules/approximators/SkolemTermsManager.java @@ -87,6 +87,13 @@ public class SkolemTermsManager { return individualToDepth_map.keySet().size(); } + /** + * Just for reading the clause id from LimitedSkolemisationApproximator. + */ + int getClauseId(DLClause clause) { + return clauseToId_map.get(clause); + } + private int mapClauseToId(DLClause clause) { if(!clauseToId_map.containsKey(clause)) { clauseToId_map.put(clause, termsCounter); diff --git a/src/uk/ac/ox/cs/pagoda/util/PagodaProperties.java b/src/uk/ac/ox/cs/pagoda/util/PagodaProperties.java index e07d54f..2c53063 100644 --- a/src/uk/ac/ox/cs/pagoda/util/PagodaProperties.java +++ b/src/uk/ac/ox/cs/pagoda/util/PagodaProperties.java @@ -5,6 +5,8 @@ import org.apache.log4j.Logger; import java.io.FileInputStream; import java.io.IOException; import java.io.InputStream; +import java.nio.file.Path; +import java.nio.file.Paths; import java.util.Properties; public class PagodaProperties { @@ -13,6 +15,7 @@ public class PagodaProperties { public static final boolean DEFAULT_DEBUG = false; private static final boolean DEFAULT_USE_ALWAYS_SIMPLE_UPPER_BOUND; private static final boolean DEFAULT_USE_SKOLEM_UPPER_BOUND; + private static final Path DEFAULT_STATISTICS_DIR; public static boolean shellModeDefault = false; private static boolean debug = DEFAULT_DEBUG; @@ -20,6 +23,7 @@ public class PagodaProperties { static { boolean defaultUseAlwaysSimpleUpperBound = false; boolean defaultUseSkolemUpperBound = true; + Path defaultStatisticsDir = null; try(InputStream in = PagodaProperties.class.getClassLoader().getResourceAsStream(CONFIG_FILE)) { Properties config = new Properties(); @@ -28,8 +32,12 @@ public class PagodaProperties { Logger logger = Logger.getLogger("PagodaProperties"); if(config.containsKey("debug")) { debug = Boolean.parseBoolean(config.getProperty("debug")); -// logger.info("Debugging mode is enabled (you can disable it from file \"pagoda.properties\")"); logger.info("Debugging mode is enabled"); + + if(config.containsKey("statisticsDir")) { + defaultStatisticsDir = Paths.get(config.getProperty("statisticsDir")); + logger.info("The directory where statistics are saved is: \"" + defaultStatisticsDir + "\""); + } } if(config.containsKey("useAlwaysSimpleUpperBound")) { defaultUseAlwaysSimpleUpperBound = @@ -40,11 +48,13 @@ public class PagodaProperties { defaultUseSkolemUpperBound = Boolean.parseBoolean(config.getProperty("useSkolemUpperBound")); logger.info("The Skolem upper bound is enabled"); } + } catch(IOException e) { e.printStackTrace(); } DEFAULT_USE_ALWAYS_SIMPLE_UPPER_BOUND = defaultUseAlwaysSimpleUpperBound; DEFAULT_USE_SKOLEM_UPPER_BOUND = defaultUseSkolemUpperBound; + DEFAULT_STATISTICS_DIR = defaultStatisticsDir; } String dataPath = null; @@ -56,6 +66,8 @@ public class PagodaProperties { boolean shellMode = shellModeDefault; private boolean useAlwaysSimpleUpperBound = DEFAULT_USE_ALWAYS_SIMPLE_UPPER_BOUND; private boolean useSkolemUpperBound = DEFAULT_USE_SKOLEM_UPPER_BOUND; + private Path statisticsDir = DEFAULT_STATISTICS_DIR; + public PagodaProperties(String path) { java.util.Properties m_properties = new java.util.Properties(); InputStream inputStream = null; @@ -92,6 +104,10 @@ public class PagodaProperties { return DEFAULT_USE_ALWAYS_SIMPLE_UPPER_BOUND; } + public static Path getDefaultStatisticsDir() { + return DEFAULT_STATISTICS_DIR; + } + public static boolean getDefaultUseSkolemUpperBound() { return DEFAULT_USE_SKOLEM_UPPER_BOUND; } @@ -167,4 +183,12 @@ public class PagodaProperties { public void setUseSkolemUpperBound(boolean flag) { useSkolemUpperBound = flag; } + + public Path getStatisticsDir() { + return statisticsDir; + } + + public void setStatisticsDir(Path statisticsDir) { + this.statisticsDir = statisticsDir; + } } diff --git a/src/uk/ac/ox/cs/pagoda/util/disposable/Disposable.java b/src/uk/ac/ox/cs/pagoda/util/disposable/Disposable.java index b208cc3..4015b66 100644 --- a/src/uk/ac/ox/cs/pagoda/util/disposable/Disposable.java +++ b/src/uk/ac/ox/cs/pagoda/util/disposable/Disposable.java @@ -25,15 +25,6 @@ public abstract class Disposable { } private class AlreadyDisposedException extends RuntimeException { - - public AlreadyDisposedException() { - super(); - } - - public AlreadyDisposedException(String msg) { - super(msg); - } } - } -- cgit v1.2.3