package uk.ac.manchester.cs.jfact.split; /* This file is part of the JFact DL reasoner Copyright 2011-2013 by Ignazio Palmisano, Dmitry Tsarkov, University of Manchester This library is free software; you can redistribute it and/or modify it under the terms of the GNU Lesser General Public License as published by the Free Software Foundation; either version 2.1 of the License, or (at your option) any later version. This library is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details. You should have received a copy of the GNU Lesser General Public License along with this library; if not, write to the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA*/ import java.io.Serializable; import java.util.ArrayList; import java.util.Collection; import java.util.Collections; import java.util.List; import uk.ac.manchester.cs.jfact.kernel.dl.interfaces.AxiomInterface; import uk.ac.manchester.cs.jfact.kernel.dl.interfaces.NamedEntity; import uk.ac.manchester.cs.jfact.kernel.options.JFactReasonerConfiguration; import conformance.Original; import conformance.PortedFrom; /** class to create modules of an ontology wrt module type */ @PortedFrom(file = "Modularity.h", name = "TModularizer") public class TModularizer implements Serializable { private static final long serialVersionUID = 11000L; /** shared signature signature */ @PortedFrom(file = "Modularity.h", name = "sig") private TSignature sig; /** internal syntactic locality checker */ @PortedFrom(file = "Modularity.h", name = "Checker") private final LocalityChecker Checker; /** module as a list of axioms */ @PortedFrom(file = "Modularity.h", name = "Module") private final List<AxiomInterface> Module = new ArrayList<AxiomInterface>(); /** pointer to a sig index; if not NULL then use optimized algo */ @PortedFrom(file = "Modularity.h", name = "sigIndex") private final SigIndex sigIndex; /** true if no atoms are processed ATM */ @PortedFrom(file = "Modularity.h", name = "noAtomsProcessing") private boolean noAtomsProcessing; /** queue of unprocessed entities */ @PortedFrom(file = "Modularity.h", name = "WorkQueue") private final List<NamedEntity> WorkQueue = new ArrayList<NamedEntity>(); /** number of locality check calls */ @PortedFrom(file = "Modularity.h", name = "nChecks") private long nChecks; /** number of non-local axioms */ @PortedFrom(file = "Modularity.h", name = "nNonLocal") private long nNonLocal; @Original private final JFactReasonerConfiguration config; /** * update SIG wrt the axiom signature * * @param axiom * axiom */ @PortedFrom(file = "Modularity.h", name = "addAxiomSig") private void addAxiomSig(AxiomInterface axiom) { TSignature axiomSig = axiom.getSignature(); if (sigIndex != null) { for (NamedEntity p : axiomSig.begin()) { if (!sig.containsNamedEntity(p)) { WorkQueue.add(p); sig.add(p); } } } } /** * add an axiom to a module * * @param axiom * axiom */ @PortedFrom(file = "Modularity.h", name = "addAxiomToModule") private void addAxiomToModule(AxiomInterface axiom) { axiom.setInModule(true); Module.add(axiom); // update the signature addAxiomSig(axiom); } /** * @param ax * ax * @return true iff an AXiom is non-local */ @PortedFrom(file = "Modularity.h", name = "isNonLocal") private boolean isNonLocal(AxiomInterface ax) { ++nChecks; if (Checker.local(ax)) { return false; } ++nNonLocal; return true; } /** * add an axiom if it is non-local (or if noCheck is true) * * @param ax * ax * @param noCheck * noCheck */ @PortedFrom(file = "Modularity.h", name = "addNonLocal") private void addNonLocal(AxiomInterface ax, boolean noCheck) { if (noCheck || isNonLocal(ax)) { addAxiomToModule(ax); if (config.isRKG_USE_AD_IN_MODULE_EXTRACTION() && noAtomsProcessing && ax.getAtom() != null) { noAtomsProcessing = false; addNonLocal(ax.getAtom().getModule(), true); noAtomsProcessing = true; } } } /** * add all the non-local axioms from given axiom-set AxSet * * @param AxSet * AxSet * @param noCheck * noCheck */ @PortedFrom(file = "Modularity.h", name = "addNonLocal") private void addNonLocal(Collection<AxiomInterface> AxSet, boolean noCheck) { for (AxiomInterface q : AxSet) { if (!q.isInModule() && q.isInSS()) { this.addNonLocal(q, noCheck); } } } /** build a module traversing axioms by a signature */ @PortedFrom(file = "Modularity.h", name = "extractModuleQueue") private void extractModuleQueue() { // init queue with a sig for (NamedEntity p : sig.begin()) { WorkQueue.add(p); } // add all the axioms that are non-local wrt given value of a // top-locality this.addNonLocal(sigIndex.getNonLocal(sig.topCLocal()), true); // main cycle while (!WorkQueue.isEmpty()) { NamedEntity entity = WorkQueue.remove(0); // for all the axioms that contains entity in their signature this.addNonLocal(sigIndex.getAxioms(entity), false); } } /** * extract module wrt presence of a sig index * * @param args * args */ @PortedFrom(file = "Modularity.h", name = "extractModule") private void extractModule(Collection<AxiomInterface> args) { Module.clear(); // clear the module flag in the input for (AxiomInterface p : args) { p.setInModule(false); } for (AxiomInterface p : args) { if (p.isUsed()) { p.setInSS(true); } } extractModuleQueue(); for (AxiomInterface p : args) { p.setInSS(false); } } /** * init c'tor * * @param config * config * @param c * c */ public TModularizer(JFactReasonerConfiguration config, LocalityChecker c) { this.config = config; Checker = c; sig = c.getSignature(); sigIndex = new SigIndex(Checker); nChecks = 0; nNonLocal = 0; } /** * allow the checker to preprocess an ontology if necessary * * @param vec * vec */ @PortedFrom(file = "Modularity.h", name = "preprocessOntology") public void preprocessOntology(Collection<AxiomInterface> vec) { Checker.preprocessOntology(vec); sigIndex.clear(); sigIndex.preprocessOntology(vec); nChecks += 2 * vec.size(); } /** * @param ax * ax * @param type * type * @return true iff the axiom AX is a tautology wrt given type */ @PortedFrom(file = "Modularity.h", name = "isTautology") public boolean isTautology(AxiomInterface ax, ModuleType type) { boolean topLocality = type == ModuleType.M_TOP; sig = ax.getSignature(); sig.setLocality(topLocality); // axiom is a tautology if it is local wrt its own signature boolean toReturn = Checker.local(ax); if (type != ModuleType.M_STAR || !toReturn) { return toReturn; } // here it is STAR case and AX is local wrt BOT sig.setLocality(!topLocality); return Checker.local(ax); } /** @return sigIndex (mainly to (un-)register axioms on the fly) */ @PortedFrom(file = "Modularity.h", name = "getSigIndex") public SigIndex getSigIndex() { return sigIndex; } /** @return Locality checker */ @PortedFrom(file = "Modularity.h", name = "getLocalityChecker") public LocalityChecker getLocalityChecker() { return Checker; } /** * @param begin * begin * @param signature * signature * @param type * type */ @PortedFrom(file = "Modularity.h", name = "extract") public void extract(AxiomInterface begin, TSignature signature, ModuleType type) { this.extract(Collections.singletonList(begin), signature, type); } /** * extract module wrt SIGNATURE and TYPE from the set of axioms [BEGIN,END) * * @param begin * begin * @param signature * signature * @param type * type */ @PortedFrom(file = "Modularity.h", name = "extract") public void extract(Collection<AxiomInterface> begin, TSignature signature, ModuleType type) { boolean topLocality = type == ModuleType.M_TOP; sig = signature; Checker.setSignatureValue(sig); sig.setLocality(topLocality); this.extractModule(begin); if (type != ModuleType.M_STAR) { return; } // here there is a star: do the cycle until stabilization int size; List<AxiomInterface> oldModule = new ArrayList<AxiomInterface>(); do { size = Module.size(); oldModule.clear(); oldModule.addAll(Module); topLocality = !topLocality; sig = signature; sig.setLocality(topLocality); this.extractModule(oldModule); } while (size != Module.size()); } /** @return get number of checks made */ @PortedFrom(file = "Modularity.h", name = "getNChecks") public long getNChecks() { return nChecks; } /** * extract module wrt SIGNATURE and TYPE from O; * * @param list * list * @param signature * signature * @param type * type * @return result in the Set */ @PortedFrom(file = "Modularity.h", name = "extractModule") public List<AxiomInterface> extractModule(List<AxiomInterface> list, TSignature signature, ModuleType type) { this.extract(list, signature, type); return Module; } /** @return the last computed module */ @PortedFrom(file = "Modularity.h", name = "getModule") public List<AxiomInterface> getModule() { return Module; } /** @return signature */ @PortedFrom(file = "Modularity.h", name = "getSignature") public TSignature getSignature() { return sig; } }