From: <lor...@us...> - 2011-08-08 13:35:22
|
Revision: 3013 http://dl-learner.svn.sourceforge.net/dl-learner/?rev=3013&view=rev Author: lorenz_b Date: 2011-08-08 13:35:14 +0000 (Mon, 08 Aug 2011) Log Message: ----------- Continued algorithms. Added more OWL axioms. Modified Paths: -------------- trunk/components-core/src/main/java/org/dllearner/algorithms/properties/DisjointPropertyAxiomLearner.java trunk/components-core/src/main/java/org/dllearner/algorithms/properties/PropertyDomainAxiomLearner.java trunk/components-core/src/main/java/org/dllearner/algorithms/properties/SubPropertyOfAxiomLearner.java trunk/components-core/src/main/java/org/dllearner/core/owl/PropertyAxiomVisitor.java trunk/components-core/src/main/java/org/dllearner/kb/sparql/SparqlQuery.java trunk/components-core/src/main/java/org/dllearner/utilities/owl/OWLAPIAxiomConvertVisitor.java Added Paths: ----------- trunk/components-core/src/main/java/org/dllearner/algorithms/properties/DataPropertyDomainAxiomLearner.java trunk/components-core/src/main/java/org/dllearner/algorithms/properties/DataPropertyRangeAxiomLearner.java trunk/components-core/src/main/java/org/dllearner/algorithms/properties/DisjointDataPropertyAxiomLearner.java trunk/components-core/src/main/java/org/dllearner/algorithms/properties/EquivalentDataPropertyAxiomLearner.java trunk/components-core/src/main/java/org/dllearner/algorithms/properties/FunctionalDataPropertyAxiomLearner.java trunk/components-core/src/main/java/org/dllearner/algorithms/properties/SubDataPropertyOfAxiomLearner.java trunk/components-core/src/main/java/org/dllearner/core/config/DataPropertyEditor.java trunk/components-core/src/main/java/org/dllearner/core/owl/DisjointDatatypePropertyAxiom.java trunk/components-core/src/main/java/org/dllearner/core/owl/DisjointObjectPropertyAxiom.java trunk/components-core/src/main/java/org/dllearner/core/owl/FunctionalDatatypePropertyAxiom.java trunk/components-core/src/main/java/org/dllearner/core/owl/SubDatatypePropertyAxiom.java Added: trunk/components-core/src/main/java/org/dllearner/algorithms/properties/DataPropertyDomainAxiomLearner.java =================================================================== --- trunk/components-core/src/main/java/org/dllearner/algorithms/properties/DataPropertyDomainAxiomLearner.java (rev 0) +++ trunk/components-core/src/main/java/org/dllearner/algorithms/properties/DataPropertyDomainAxiomLearner.java 2011-08-08 13:35:14 UTC (rev 3013) @@ -0,0 +1,233 @@ +package org.dllearner.algorithms.properties; + +import java.util.ArrayList; +import java.util.Comparator; +import java.util.HashMap; +import java.util.HashSet; +import java.util.Iterator; +import java.util.List; +import java.util.Map; +import java.util.Map.Entry; +import java.util.Set; +import java.util.SortedSet; +import java.util.TreeSet; + +import org.dllearner.core.AbstractComponent; +import org.dllearner.core.AxiomLearningAlgorithm; +import org.dllearner.core.ComponentAnn; +import org.dllearner.core.ComponentInitException; +import org.dllearner.core.EvaluatedAxiom; +import org.dllearner.core.config.ConfigOption; +import org.dllearner.core.config.IntegerEditor; +import org.dllearner.core.configurators.Configurator; +import org.dllearner.core.owl.Axiom; +import org.dllearner.core.owl.DatatypeProperty; +import org.dllearner.core.owl.DatatypePropertyDomainAxiom; +import org.dllearner.core.owl.Description; +import org.dllearner.core.owl.Individual; +import org.dllearner.core.owl.NamedClass; +import org.dllearner.kb.SparqlEndpointKS; +import org.dllearner.kb.sparql.ExtendedQueryEngineHTTP; +import org.dllearner.learningproblems.AxiomScore; +import org.dllearner.reasoning.SPARQLReasoner; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; + +import com.hp.hpl.jena.query.QuerySolution; +import com.hp.hpl.jena.query.ResultSet; + +@ComponentAnn(name="property domain axiom learner") +public class DataPropertyDomainAxiomLearner extends AbstractComponent implements AxiomLearningAlgorithm { + + private static final Logger logger = LoggerFactory.getLogger(DataPropertyDomainAxiomLearner.class); + + @ConfigOption(name="propertyToDescribe", description="", propertyEditorClass=DatatypeProperty.class) + private DatatypeProperty propertyToDescribe; + @ConfigOption(name="maxExecutionTimeInSeconds", description="", propertyEditorClass=IntegerEditor.class) + private int maxExecutionTimeInSeconds = 10; + @ConfigOption(name="maxFetchedRows", description="The maximum number of rows fetched from the endpoint to approximate the result.", propertyEditorClass=IntegerEditor.class) + private int maxFetchedRows = 0; + + private SPARQLReasoner reasoner; + private SparqlEndpointKS ks; + + private List<EvaluatedAxiom> currentlyBestAxioms; + private long startTime; + private int fetchedRows; + + public DataPropertyDomainAxiomLearner(SparqlEndpointKS ks){ + this.ks = ks; + } + + public int getMaxExecutionTimeInSeconds() { + return maxExecutionTimeInSeconds; + } + + public void setMaxExecutionTimeInSeconds(int maxExecutionTimeInSeconds) { + this.maxExecutionTimeInSeconds = maxExecutionTimeInSeconds; + } + + public DatatypeProperty getPropertyToDescribe() { + return propertyToDescribe; + } + + public void setPropertyToDescribe(DatatypeProperty propertyToDescribe) { + this.propertyToDescribe = propertyToDescribe; + } + + public int getMaxFetchedRows() { + return maxFetchedRows; + } + + public void setMaxFetchedRows(int maxFetchedRows) { + this.maxFetchedRows = maxFetchedRows; + } + + @Override + public void start() { + logger.info("Start learning..."); + startTime = System.currentTimeMillis(); + fetchedRows = 0; + currentlyBestAxioms = new ArrayList<EvaluatedAxiom>(); + //get existing domains + Description existingDomain = reasoner.getDomain(propertyToDescribe); + logger.info("Existing domain: " + existingDomain); + + //get subjects with types + Map<Individual, Set<NamedClass>> individual2Types = new HashMap<Individual, Set<NamedClass>>(); + Map<Individual, Set<NamedClass>> newIndividual2Types; + boolean repeat = true; + while(!terminationCriteriaSatisfied() && repeat){ + newIndividual2Types = getSubjectsWithTypes(fetchedRows); + individual2Types.putAll(newIndividual2Types); + currentlyBestAxioms = buildBestAxioms(individual2Types); + fetchedRows += 1000; + repeat = !newIndividual2Types.isEmpty(); + } + logger.info("...finished in {}ms.", (System.currentTimeMillis()-startTime)); + } + + @Override + public List<Axiom> getCurrentlyBestAxioms(int nrOfAxioms) { + List<Axiom> bestAxioms = new ArrayList<Axiom>(); + + Iterator<EvaluatedAxiom> it = currentlyBestAxioms.iterator(); + while(bestAxioms.size() < nrOfAxioms && it.hasNext()){ + bestAxioms.add(it.next().getAxiom()); + } + + return bestAxioms; + } + + @Override + public List<EvaluatedAxiom> getCurrentlyBestEvaluatedAxioms(int nrOfAxioms) { + int max = Math.min(currentlyBestAxioms.size(), nrOfAxioms); + + List<EvaluatedAxiom> bestAxioms = currentlyBestAxioms.subList(0, max); + + return bestAxioms; + } + + @Override + public Configurator getConfigurator() { + // TODO Auto-generated method stub + return null; + } + + @Override + public void init() throws ComponentInitException { + reasoner = new SPARQLReasoner(ks); + + } + + private boolean terminationCriteriaSatisfied(){ + boolean timeLimitExceeded = maxExecutionTimeInSeconds == 0 ? false : (System.currentTimeMillis() - startTime) >= maxExecutionTimeInSeconds * 1000; + boolean resultLimitExceeded = maxFetchedRows == 0 ? false : fetchedRows >= maxFetchedRows; + return timeLimitExceeded || resultLimitExceeded; + } + + private List<EvaluatedAxiom> buildBestAxioms(Map<Individual, Set<NamedClass>> individual2Types){ + List<EvaluatedAxiom> axioms = new ArrayList<EvaluatedAxiom>(); + Map<NamedClass, Integer> result = new HashMap<NamedClass, Integer>(); + for(Entry<Individual, Set<NamedClass>> entry : individual2Types.entrySet()){ + for(NamedClass nc : entry.getValue()){ + Integer cnt = result.get(nc); + if(cnt == null){ + cnt = Integer.valueOf(1); + } + result.put(nc, Integer.valueOf(cnt + 1)); + } + } + + EvaluatedAxiom evalAxiom; + for(Entry<NamedClass, Integer> entry : sortByValues(result)){ + evalAxiom = new EvaluatedAxiom(new DatatypePropertyDomainAxiom(propertyToDescribe, entry.getKey()), + new AxiomScore(entry.getValue() / (double)individual2Types.keySet().size())); + axioms.add(evalAxiom); + } + + return axioms; + } + + /* + * Returns the entries of the map sorted by value. + */ + private SortedSet<Entry<NamedClass, Integer>> sortByValues(Map<NamedClass, Integer> map){ + SortedSet<Entry<NamedClass, Integer>> sortedSet = new TreeSet<Map.Entry<NamedClass,Integer>>(new Comparator<Entry<NamedClass, Integer>>() { + + @Override + public int compare(Entry<NamedClass, Integer> value1, Entry<NamedClass, Integer> value2) { + if(value1.getValue() < value2.getValue()){ + return 1; + } else if(value2.getValue() < value1.getValue()){ + return -1; + } else { + return value1.getKey().compareTo(value2.getKey()); + } + } + }); + sortedSet.addAll(map.entrySet()); + return sortedSet; + } + + private Map<Individual, Set<NamedClass>> getSubjectsWithTypes(int offset){ + Map<Individual, Set<NamedClass>> individual2Types = new HashMap<Individual, Set<NamedClass>>(); + int limit = 1000; + String query = String.format("SELECT ?ind ?type WHERE {?ind <%s> ?o. ?ind a ?type.} LIMIT %d OFFSET %d", propertyToDescribe.getURI().toString(), limit, offset); + ResultSet rs = executeQuery(query); + QuerySolution qs; + Individual ind; + Set<NamedClass> types; + while(rs.hasNext()){ + qs = rs.next(); + ind = new Individual(qs.getResource("ind").getURI()); + types = individual2Types.get(ind); + if(types == null){ + types = new HashSet<NamedClass>(); + individual2Types.put(ind, types); + } + types.add(new NamedClass(qs.getResource("type").getURI())); + } + return individual2Types; + } + + /* + * Executes a SELECT query and returns the result. + */ + private ResultSet executeQuery(String query){ + logger.info("Sending query \n {}", query); + + ExtendedQueryEngineHTTP queryExecution = new ExtendedQueryEngineHTTP(ks.getEndpoint().getURL().toString(), query); + queryExecution.setTimeout(maxExecutionTimeInSeconds * 1000); + for (String dgu : ks.getEndpoint().getDefaultGraphURIs()) { + queryExecution.addDefaultGraph(dgu); + } + for (String ngu : ks.getEndpoint().getNamedGraphURIs()) { + queryExecution.addNamedGraph(ngu); + } + ResultSet resultSet = queryExecution.execSelect(); + return resultSet; + } + + +} Added: trunk/components-core/src/main/java/org/dllearner/algorithms/properties/DataPropertyRangeAxiomLearner.java =================================================================== --- trunk/components-core/src/main/java/org/dllearner/algorithms/properties/DataPropertyRangeAxiomLearner.java (rev 0) +++ trunk/components-core/src/main/java/org/dllearner/algorithms/properties/DataPropertyRangeAxiomLearner.java 2011-08-08 13:35:14 UTC (rev 3013) @@ -0,0 +1,234 @@ +package org.dllearner.algorithms.properties; + +import java.util.ArrayList; +import java.util.Comparator; +import java.util.HashMap; +import java.util.HashSet; +import java.util.Iterator; +import java.util.List; +import java.util.Map; +import java.util.Map.Entry; +import java.util.Set; +import java.util.SortedSet; +import java.util.TreeSet; + +import org.dllearner.core.AxiomLearningAlgorithm; +import org.dllearner.core.AbstractComponent; +import org.dllearner.core.ComponentAnn; +import org.dllearner.core.ComponentInitException; +import org.dllearner.core.EvaluatedAxiom; +import org.dllearner.core.config.ConfigOption; +import org.dllearner.core.config.IntegerEditor; +import org.dllearner.core.config.ObjectPropertyEditor; +import org.dllearner.core.configurators.Configurator; +import org.dllearner.core.owl.Axiom; +import org.dllearner.core.owl.Description; +import org.dllearner.core.owl.Individual; +import org.dllearner.core.owl.NamedClass; +import org.dllearner.core.owl.ObjectProperty; +import org.dllearner.core.owl.ObjectPropertyRangeAxiom; +import org.dllearner.kb.SparqlEndpointKS; +import org.dllearner.kb.sparql.ExtendedQueryEngineHTTP; +import org.dllearner.learningproblems.AxiomScore; +import org.dllearner.reasoning.SPARQLReasoner; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; + +import com.hp.hpl.jena.query.QuerySolution; +import com.hp.hpl.jena.query.ResultSet; +import com.hp.hpl.jena.sparql.engine.http.QueryEngineHTTP; + +@ComponentAnn(name="property range learner") +public class DataPropertyRangeAxiomLearner extends AbstractComponent implements AxiomLearningAlgorithm { + + private static final Logger logger = LoggerFactory.getLogger(DataPropertyRangeAxiomLearner.class); + + @ConfigOption(name="propertyToDescribe", description="", propertyEditorClass=ObjectPropertyEditor.class) + private ObjectProperty propertyToDescribe; + @ConfigOption(name="maxExecutionTimeInSeconds", description="", propertyEditorClass=IntegerEditor.class) + private int maxExecutionTimeInSeconds = 10; + @ConfigOption(name="maxFetchedRows", description="The maximum number of rows fetched from the endpoint to approximate the result.", propertyEditorClass=IntegerEditor.class) + private int maxFetchedRows = 0; + + private SPARQLReasoner reasoner; + private SparqlEndpointKS ks; + + private List<EvaluatedAxiom> currentlyBestAxioms; + private long startTime; + private int fetchedRows; + + public DataPropertyRangeAxiomLearner(SparqlEndpointKS ks){ + this.ks = ks; + } + + public int getMaxExecutionTimeInSeconds() { + return maxExecutionTimeInSeconds; + } + + public void setMaxExecutionTimeInSeconds(int maxExecutionTimeInSeconds) { + this.maxExecutionTimeInSeconds = maxExecutionTimeInSeconds; + } + + public ObjectProperty getPropertyToDescribe() { + return propertyToDescribe; + } + + public void setPropertyToDescribe(ObjectProperty propertyToDescribe) { + this.propertyToDescribe = propertyToDescribe; + } + + public int getMaxFetchedRows() { + return maxFetchedRows; + } + + public void setMaxFetchedRows(int maxFetchedRows) { + this.maxFetchedRows = maxFetchedRows; + } + + @Override + public void start() { + logger.info("Start learning..."); + startTime = System.currentTimeMillis(); + fetchedRows = 0; + currentlyBestAxioms = new ArrayList<EvaluatedAxiom>(); + //get existing range + Description existingRange = reasoner.getRange(propertyToDescribe); + logger.debug("Existing range: " + existingRange); + + //get objects with types + Map<Individual, Set<NamedClass>> individual2Types = new HashMap<Individual, Set<NamedClass>>(); + Map<Individual, Set<NamedClass>> newIndividual2Types; + boolean repeat = true; + while(!terminationCriteriaSatisfied() && repeat){ + newIndividual2Types = getObjectsWithTypes(fetchedRows); + individual2Types.putAll(newIndividual2Types); + currentlyBestAxioms = buildBestAxioms(individual2Types); + fetchedRows += 1000; + repeat = !newIndividual2Types.isEmpty(); + } + logger.info("...finished in {}ms.", (System.currentTimeMillis()-startTime)); + } + + @Override + public List<Axiom> getCurrentlyBestAxioms(int nrOfAxioms) { + List<Axiom> bestAxioms = new ArrayList<Axiom>(); + + Iterator<EvaluatedAxiom> it = currentlyBestAxioms.iterator(); + while(bestAxioms.size() < nrOfAxioms && it.hasNext()){ + bestAxioms.add(it.next().getAxiom()); + } + + return bestAxioms; + } + + @Override + public List<EvaluatedAxiom> getCurrentlyBestEvaluatedAxioms(int nrOfAxioms) { + int max = Math.min(currentlyBestAxioms.size(), nrOfAxioms); + + List<EvaluatedAxiom> bestAxioms = currentlyBestAxioms.subList(0, max); + + return bestAxioms; + } + + @Override + public Configurator getConfigurator() { + // TODO Auto-generated method stub + return null; + } + + @Override + public void init() throws ComponentInitException { + reasoner = new SPARQLReasoner(ks); + + } + + private boolean terminationCriteriaSatisfied(){ + boolean timeLimitExceeded = maxExecutionTimeInSeconds == 0 ? false : (System.currentTimeMillis() - startTime) >= maxExecutionTimeInSeconds * 1000; + boolean resultLimitExceeded = maxFetchedRows == 0 ? false : fetchedRows >= maxFetchedRows; + return timeLimitExceeded || resultLimitExceeded; + } + + private List<EvaluatedAxiom> buildBestAxioms(Map<Individual, Set<NamedClass>> individual2Types){ + List<EvaluatedAxiom> axioms = new ArrayList<EvaluatedAxiom>(); + Map<NamedClass, Integer> result = new HashMap<NamedClass, Integer>(); + for(Entry<Individual, Set<NamedClass>> entry : individual2Types.entrySet()){ + for(NamedClass nc : entry.getValue()){ + Integer cnt = result.get(nc); + if(cnt == null){ + cnt = Integer.valueOf(1); + } + result.put(nc, Integer.valueOf(cnt + 1)); + } + } + + EvaluatedAxiom evalAxiom; + for(Entry<NamedClass, Integer> entry : sortByValues(result)){ + evalAxiom = new EvaluatedAxiom(new ObjectPropertyRangeAxiom(propertyToDescribe, entry.getKey()), + new AxiomScore(entry.getValue() / (double)individual2Types.keySet().size())); + axioms.add(evalAxiom); + } + + return axioms; + } + + /* + * Returns the entries of the map sorted by value. + */ + private SortedSet<Entry<NamedClass, Integer>> sortByValues(Map<NamedClass, Integer> map){ + SortedSet<Entry<NamedClass, Integer>> sortedSet = new TreeSet<Map.Entry<NamedClass,Integer>>(new Comparator<Entry<NamedClass, Integer>>() { + + @Override + public int compare(Entry<NamedClass, Integer> value1, Entry<NamedClass, Integer> value2) { + if(value1.getValue() < value2.getValue()){ + return 1; + } else if(value2.getValue() < value1.getValue()){ + return -1; + } else { + return value1.getKey().compareTo(value2.getKey()); + } + } + }); + sortedSet.addAll(map.entrySet()); + return sortedSet; + } + + private Map<Individual, Set<NamedClass>> getObjectsWithTypes(int offset){ + Map<Individual, Set<NamedClass>> individual2Types = new HashMap<Individual, Set<NamedClass>>(); + int limit = 1000; + String query = String.format("SELECT ?ind ?type WHERE {?s <%s> ?ind. ?ind a ?type.} LIMIT %d OFFSET %d", propertyToDescribe.getName(), limit, offset); + ResultSet rs = executeQuery(query); + QuerySolution qs; + Individual ind; + Set<NamedClass> types; + while(rs.hasNext()){ + qs = rs.next(); + ind = new Individual(qs.getResource("ind").getURI()); + types = individual2Types.get(ind); + if(types == null){ + types = new HashSet<NamedClass>(); + individual2Types.put(ind, types); + } + types.add(new NamedClass(qs.getResource("type").getURI())); + } + return individual2Types; + } + + /* + * Executes a SELECT query and returns the result. + */ + private ResultSet executeQuery(String query){ + logger.info("Sending query \n {}", query); + + ExtendedQueryEngineHTTP queryExecution = new ExtendedQueryEngineHTTP(ks.getEndpoint().getURL().toString(), query); + queryExecution.setTimeout(maxExecutionTimeInSeconds * 1000); + for (String dgu : ks.getEndpoint().getDefaultGraphURIs()) { + queryExecution.addDefaultGraph(dgu); + } + for (String ngu : ks.getEndpoint().getNamedGraphURIs()) { + queryExecution.addNamedGraph(ngu); + } + ResultSet resultSet = queryExecution.execSelect(); + return resultSet; + } + +} Added: trunk/components-core/src/main/java/org/dllearner/algorithms/properties/DisjointDataPropertyAxiomLearner.java =================================================================== --- trunk/components-core/src/main/java/org/dllearner/algorithms/properties/DisjointDataPropertyAxiomLearner.java (rev 0) +++ trunk/components-core/src/main/java/org/dllearner/algorithms/properties/DisjointDataPropertyAxiomLearner.java 2011-08-08 13:35:14 UTC (rev 3013) @@ -0,0 +1,143 @@ +package org.dllearner.algorithms.properties; + +import java.util.ArrayList; +import java.util.Iterator; +import java.util.List; + +import org.dllearner.core.AbstractComponent; +import org.dllearner.core.AxiomLearningAlgorithm; +import org.dllearner.core.ComponentAnn; +import org.dllearner.core.ComponentInitException; +import org.dllearner.core.EvaluatedAxiom; +import org.dllearner.core.config.ConfigOption; +import org.dllearner.core.config.DataPropertyEditor; +import org.dllearner.core.config.IntegerEditor; +import org.dllearner.core.configurators.Configurator; +import org.dllearner.core.owl.Axiom; +import org.dllearner.core.owl.DatatypeProperty; +import org.dllearner.kb.SparqlEndpointKS; +import org.dllearner.kb.sparql.ExtendedQueryEngineHTTP; +import org.dllearner.reasoning.SPARQLReasoner; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; + +import com.hp.hpl.jena.query.ResultSet; + +@ComponentAnn(name="disjoint property axiom learner") +public class DisjointDataPropertyAxiomLearner extends AbstractComponent implements AxiomLearningAlgorithm { + + private static final Logger logger = LoggerFactory.getLogger(PropertyDomainAxiomLearner.class); + + @ConfigOption(name="propertyToDescribe", description="", propertyEditorClass=DataPropertyEditor.class) + private DatatypeProperty propertyToDescribe; + @ConfigOption(name="maxExecutionTimeInSeconds", description="", propertyEditorClass=IntegerEditor.class) + private int maxExecutionTimeInSeconds = 10; + @ConfigOption(name="maxFetchedRows", description="The maximum number of rows fetched from the endpoint to approximate the result.", propertyEditorClass=IntegerEditor.class) + private int maxFetchedRows = 0; + + private SPARQLReasoner reasoner; + private SparqlEndpointKS ks; + + private List<EvaluatedAxiom> currentlyBestAxioms; + private long startTime; + private int fetchedRows; + + public DisjointDataPropertyAxiomLearner(SparqlEndpointKS ks){ + this.ks = ks; + } + + public int getMaxExecutionTimeInSeconds() { + return maxExecutionTimeInSeconds; + } + + public void setMaxExecutionTimeInSeconds(int maxExecutionTimeInSeconds) { + this.maxExecutionTimeInSeconds = maxExecutionTimeInSeconds; + } + + public DatatypeProperty getPropertyToDescribe() { + return propertyToDescribe; + } + + public void setPropertyToDescribe(DatatypeProperty propertyToDescribe) { + this.propertyToDescribe = propertyToDescribe; + } + + public int getMaxFetchedRows() { + return maxFetchedRows; + } + + public void setMaxFetchedRows(int maxFetchedRows) { + this.maxFetchedRows = maxFetchedRows; + } + + @Override + public void start() { + logger.info("Start learning..."); + startTime = System.currentTimeMillis(); + fetchedRows = 0; + currentlyBestAxioms = new ArrayList<EvaluatedAxiom>(); + + //TODO + + logger.info("...finished in {}ms.", (System.currentTimeMillis()-startTime)); + } + + @Override + public List<Axiom> getCurrentlyBestAxioms(int nrOfAxioms) { + List<Axiom> bestAxioms = new ArrayList<Axiom>(); + + Iterator<EvaluatedAxiom> it = currentlyBestAxioms.iterator(); + while(bestAxioms.size() < nrOfAxioms && it.hasNext()){ + bestAxioms.add(it.next().getAxiom()); + } + + return bestAxioms; + } + + @Override + public List<EvaluatedAxiom> getCurrentlyBestEvaluatedAxioms(int nrOfAxioms) { + int max = Math.min(currentlyBestAxioms.size(), nrOfAxioms); + + List<EvaluatedAxiom> bestAxioms = currentlyBestAxioms.subList(0, max); + + return bestAxioms; + } + + @Override + public Configurator getConfigurator() { + // TODO Auto-generated method stub + return null; + } + + @Override + public void init() throws ComponentInitException { + reasoner = new SPARQLReasoner(ks); + + } + + private boolean terminationCriteriaSatisfied(){ + boolean timeLimitExceeded = maxExecutionTimeInSeconds == 0 ? false : (System.currentTimeMillis() - startTime) >= maxExecutionTimeInSeconds * 1000; + boolean resultLimitExceeded = maxFetchedRows == 0 ? false : fetchedRows >= maxFetchedRows; + return timeLimitExceeded || resultLimitExceeded; + } + + + /* + * Executes a SELECT query and returns the result. + */ + private ResultSet executeQuery(String query){ + logger.info("Sending query \n {}", query); + + ExtendedQueryEngineHTTP queryExecution = new ExtendedQueryEngineHTTP(ks.getEndpoint().getURL().toString(), query); + queryExecution.setTimeout(maxExecutionTimeInSeconds * 1000); + for (String dgu : ks.getEndpoint().getDefaultGraphURIs()) { + queryExecution.addDefaultGraph(dgu); + } + for (String ngu : ks.getEndpoint().getNamedGraphURIs()) { + queryExecution.addNamedGraph(ngu); + } + ResultSet resultSet = queryExecution.execSelect(); + return resultSet; + } + +} Modified: trunk/components-core/src/main/java/org/dllearner/algorithms/properties/DisjointPropertyAxiomLearner.java =================================================================== --- trunk/components-core/src/main/java/org/dllearner/algorithms/properties/DisjointPropertyAxiomLearner.java 2011-08-08 06:59:56 UTC (rev 3012) +++ trunk/components-core/src/main/java/org/dllearner/algorithms/properties/DisjointPropertyAxiomLearner.java 2011-08-08 13:35:14 UTC (rev 3013) @@ -1,44 +1,107 @@ package org.dllearner.algorithms.properties; +import java.util.ArrayList; +import java.util.Iterator; import java.util.List; +import org.dllearner.core.AbstractComponent; import org.dllearner.core.AxiomLearningAlgorithm; -import org.dllearner.core.AbstractComponent; import org.dllearner.core.ComponentAnn; import org.dllearner.core.ComponentInitException; import org.dllearner.core.EvaluatedAxiom; +import org.dllearner.core.config.ConfigOption; +import org.dllearner.core.config.IntegerEditor; +import org.dllearner.core.config.ObjectPropertyEditor; import org.dllearner.core.configurators.Configurator; import org.dllearner.core.owl.Axiom; +import org.dllearner.core.owl.ObjectProperty; import org.dllearner.kb.SparqlEndpointKS; +import org.dllearner.kb.sparql.ExtendedQueryEngineHTTP; +import org.dllearner.reasoning.SPARQLReasoner; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; +import com.hp.hpl.jena.query.ResultSet; + @ComponentAnn(name="disjoint property axiom learner") public class DisjointPropertyAxiomLearner extends AbstractComponent implements AxiomLearningAlgorithm { - private String propertyToDescribe; + private static final Logger logger = LoggerFactory.getLogger(PropertyDomainAxiomLearner.class); - public String getPropertyToDescribe() { + @ConfigOption(name="propertyToDescribe", description="", propertyEditorClass=ObjectPropertyEditor.class) + private ObjectProperty propertyToDescribe; + @ConfigOption(name="maxExecutionTimeInSeconds", description="", propertyEditorClass=IntegerEditor.class) + private int maxExecutionTimeInSeconds = 10; + @ConfigOption(name="maxFetchedRows", description="The maximum number of rows fetched from the endpoint to approximate the result.", propertyEditorClass=IntegerEditor.class) + private int maxFetchedRows = 0; + + private SPARQLReasoner reasoner; + private SparqlEndpointKS ks; + + private List<EvaluatedAxiom> currentlyBestAxioms; + private long startTime; + private int fetchedRows; + + public DisjointPropertyAxiomLearner(SparqlEndpointKS ks){ + this.ks = ks; + } + + public int getMaxExecutionTimeInSeconds() { + return maxExecutionTimeInSeconds; + } + + public void setMaxExecutionTimeInSeconds(int maxExecutionTimeInSeconds) { + this.maxExecutionTimeInSeconds = maxExecutionTimeInSeconds; + } + + public ObjectProperty getPropertyToDescribe() { return propertyToDescribe; } - public void setPropertyToDescribe(String propertyToDescribe) { + public void setPropertyToDescribe(ObjectProperty propertyToDescribe) { this.propertyToDescribe = propertyToDescribe; } + + public int getMaxFetchedRows() { + return maxFetchedRows; + } - public DisjointPropertyAxiomLearner(SparqlEndpointKS ks){ - + public void setMaxFetchedRows(int maxFetchedRows) { + this.maxFetchedRows = maxFetchedRows; } - + @Override public void start() { - // TODO Auto-generated method stub - + logger.info("Start learning..."); + startTime = System.currentTimeMillis(); + fetchedRows = 0; + currentlyBestAxioms = new ArrayList<EvaluatedAxiom>(); + + //TODO + + logger.info("...finished in {}ms.", (System.currentTimeMillis()-startTime)); } @Override public List<Axiom> getCurrentlyBestAxioms(int nrOfAxioms) { - // TODO Auto-generated method stub - return null; + List<Axiom> bestAxioms = new ArrayList<Axiom>(); + + Iterator<EvaluatedAxiom> it = currentlyBestAxioms.iterator(); + while(bestAxioms.size() < nrOfAxioms && it.hasNext()){ + bestAxioms.add(it.next().getAxiom()); + } + + return bestAxioms; } + + @Override + public List<EvaluatedAxiom> getCurrentlyBestEvaluatedAxioms(int nrOfAxioms) { + int max = Math.min(currentlyBestAxioms.size(), nrOfAxioms); + + List<EvaluatedAxiom> bestAxioms = currentlyBestAxioms.subList(0, max); + + return bestAxioms; + } @Override public Configurator getConfigurator() { @@ -48,14 +111,33 @@ @Override public void init() throws ComponentInitException { - // TODO Auto-generated method stub + reasoner = new SPARQLReasoner(ks); } - - @Override - public List<EvaluatedAxiom> getCurrentlyBestEvaluatedAxioms(int nrOfAxioms) { - // TODO Auto-generated method stub - return null; + + private boolean terminationCriteriaSatisfied(){ + boolean timeLimitExceeded = maxExecutionTimeInSeconds == 0 ? false : (System.currentTimeMillis() - startTime) >= maxExecutionTimeInSeconds * 1000; + boolean resultLimitExceeded = maxFetchedRows == 0 ? false : fetchedRows >= maxFetchedRows; + return timeLimitExceeded || resultLimitExceeded; } + + + /* + * Executes a SELECT query and returns the result. + */ + private ResultSet executeQuery(String query){ + logger.info("Sending query \n {}", query); + + ExtendedQueryEngineHTTP queryExecution = new ExtendedQueryEngineHTTP(ks.getEndpoint().getURL().toString(), query); + queryExecution.setTimeout(maxExecutionTimeInSeconds * 1000); + for (String dgu : ks.getEndpoint().getDefaultGraphURIs()) { + queryExecution.addDefaultGraph(dgu); + } + for (String ngu : ks.getEndpoint().getNamedGraphURIs()) { + queryExecution.addNamedGraph(ngu); + } + ResultSet resultSet = queryExecution.execSelect(); + return resultSet; + } } Added: trunk/components-core/src/main/java/org/dllearner/algorithms/properties/EquivalentDataPropertyAxiomLearner.java =================================================================== --- trunk/components-core/src/main/java/org/dllearner/algorithms/properties/EquivalentDataPropertyAxiomLearner.java (rev 0) +++ trunk/components-core/src/main/java/org/dllearner/algorithms/properties/EquivalentDataPropertyAxiomLearner.java 2011-08-08 13:35:14 UTC (rev 3013) @@ -0,0 +1,225 @@ +package org.dllearner.algorithms.properties; + +import java.util.ArrayList; +import java.util.Comparator; +import java.util.HashMap; +import java.util.Iterator; +import java.util.List; +import java.util.Map; +import java.util.Map.Entry; +import java.util.SortedSet; +import java.util.TreeSet; + +import org.dllearner.core.AbstractComponent; +import org.dllearner.core.AxiomLearningAlgorithm; +import org.dllearner.core.ComponentAnn; +import org.dllearner.core.ComponentInitException; +import org.dllearner.core.EvaluatedAxiom; +import org.dllearner.core.config.ConfigOption; +import org.dllearner.core.config.DataPropertyEditor; +import org.dllearner.core.config.IntegerEditor; +import org.dllearner.core.configurators.Configurator; +import org.dllearner.core.owl.Axiom; +import org.dllearner.core.owl.DatatypeProperty; +import org.dllearner.core.owl.EquivalentDatatypePropertiesAxiom; +import org.dllearner.kb.SparqlEndpointKS; +import org.dllearner.kb.sparql.ExtendedQueryEngineHTTP; +import org.dllearner.learningproblems.AxiomScore; +import org.dllearner.reasoning.SPARQLReasoner; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; + +import com.hp.hpl.jena.query.QuerySolution; +import com.hp.hpl.jena.query.ResultSet; + +@ComponentAnn(name="equivalent property axiom learner") +public class EquivalentDataPropertyAxiomLearner extends AbstractComponent implements AxiomLearningAlgorithm { + + private static final Logger logger = LoggerFactory.getLogger(EquivalentDataPropertyAxiomLearner.class); + + @ConfigOption(name="propertyToDescribe", description="", propertyEditorClass=DataPropertyEditor.class) + private DatatypeProperty propertyToDescribe; + @ConfigOption(name="maxExecutionTimeInSeconds", description="", propertyEditorClass=IntegerEditor.class) + private int maxExecutionTimeInSeconds = 10; + @ConfigOption(name="maxFetchedRows", description="The maximum number of rows fetched from the endpoint to approximate the result.", propertyEditorClass=IntegerEditor.class) + private int maxFetchedRows = 0; + + private SPARQLReasoner reasoner; + private SparqlEndpointKS ks; + + private List<EvaluatedAxiom> currentlyBestAxioms; + private long startTime; + private int fetchedRows; + + public EquivalentDataPropertyAxiomLearner(SparqlEndpointKS ks){ + this.ks = ks; + } + + public int getMaxExecutionTimeInSeconds() { + return maxExecutionTimeInSeconds; + } + + public void setMaxExecutionTimeInSeconds(int maxExecutionTimeInSeconds) { + this.maxExecutionTimeInSeconds = maxExecutionTimeInSeconds; + } + + public DatatypeProperty getPropertyToDescribe() { + return propertyToDescribe; + } + + public void setPropertyToDescribe(DatatypeProperty propertyToDescribe) { + this.propertyToDescribe = propertyToDescribe; + } + + public int getMaxFetchedRows() { + return maxFetchedRows; + } + + public void setMaxFetchedRows(int maxFetchedRows) { + this.maxFetchedRows = maxFetchedRows; + } + + @Override + public void start() { + logger.info("Start learning..."); + startTime = System.currentTimeMillis(); + fetchedRows = 0; + currentlyBestAxioms = new ArrayList<EvaluatedAxiom>(); + //get existing super properties + SortedSet<DatatypeProperty> existingSuperProperties = reasoner.getSuperProperties(propertyToDescribe); + logger.debug("Existing super properties: " + existingSuperProperties); + + //get subjects with types + int limit = 1000; + int offset = 0; + String queryTemplate = "SELECT ?p COUNT(?s) AS ?count WHERE {?s ?p ?o." + + "{SELECT ?s ?o WHERE {?s <%s> ?o.} LIMIT %d OFFSET %d}" + + "}"; + String query; + Map<DatatypeProperty, Integer> result = new HashMap<DatatypeProperty, Integer>(); + DatatypeProperty prop; + Integer oldCnt; + boolean repeat = true; + + while(!terminationCriteriaSatisfied() && repeat){ + query = String.format(queryTemplate, propertyToDescribe, limit, offset); + ResultSet rs = executeQuery(query); + QuerySolution qs; + repeat = false; + while(rs.hasNext()){ + qs = rs.next(); + prop = new DatatypeProperty(qs.getResource("p").getURI()); + int newCnt = qs.getLiteral("count").getInt(); + oldCnt = result.get(prop); + if(oldCnt == null){ + oldCnt = Integer.valueOf(newCnt); + } + result.put(prop, oldCnt); + qs.getLiteral("count").getInt(); + repeat = true; + } + if(!result.isEmpty()){ + currentlyBestAxioms = buildAxioms(result); + offset += 1000; + } + + } + + logger.info("...finished in {}ms.", (System.currentTimeMillis()-startTime)); + } + + @Override + public List<Axiom> getCurrentlyBestAxioms(int nrOfAxioms) { + List<Axiom> bestAxioms = new ArrayList<Axiom>(); + + Iterator<EvaluatedAxiom> it = currentlyBestAxioms.iterator(); + while(bestAxioms.size() < nrOfAxioms && it.hasNext()){ + bestAxioms.add(it.next().getAxiom()); + } + + return bestAxioms; + } + + @Override + public List<EvaluatedAxiom> getCurrentlyBestEvaluatedAxioms(int nrOfAxioms) { + int max = Math.min(currentlyBestAxioms.size(), nrOfAxioms); + + List<EvaluatedAxiom> bestAxioms = currentlyBestAxioms.subList(0, max); + + return bestAxioms; + } + + @Override + public Configurator getConfigurator() { + // TODO Auto-generated method stub + return null; + } + + @Override + public void init() throws ComponentInitException { + reasoner = new SPARQLReasoner(ks); + + } + + private boolean terminationCriteriaSatisfied(){ + boolean timeLimitExceeded = maxExecutionTimeInSeconds == 0 ? false : (System.currentTimeMillis() - startTime) >= maxExecutionTimeInSeconds * 1000; + boolean resultLimitExceeded = maxFetchedRows == 0 ? false : fetchedRows >= maxFetchedRows; + return timeLimitExceeded || resultLimitExceeded; + } + + private List<EvaluatedAxiom> buildAxioms(Map<DatatypeProperty, Integer> property2Count){ + List<EvaluatedAxiom> axioms = new ArrayList<EvaluatedAxiom>(); + Integer all = property2Count.get(propertyToDescribe); + property2Count.remove(propertyToDescribe); + + EvaluatedAxiom evalAxiom; + for(Entry<DatatypeProperty, Integer> entry : sortByValues(property2Count)){ + evalAxiom = new EvaluatedAxiom(new EquivalentDatatypePropertiesAxiom(propertyToDescribe, entry.getKey()), + new AxiomScore(entry.getValue() / (double)all)); + axioms.add(evalAxiom); + } + + property2Count.put(propertyToDescribe, all); + return axioms; + } + + /* + * Returns the entries of the map sorted by value. + */ + private SortedSet<Entry<DatatypeProperty, Integer>> sortByValues(Map<DatatypeProperty, Integer> map){ + SortedSet<Entry<DatatypeProperty, Integer>> sortedSet = new TreeSet<Map.Entry<DatatypeProperty,Integer>>(new Comparator<Entry<DatatypeProperty, Integer>>() { + + @Override + public int compare(Entry<DatatypeProperty, Integer> value1, Entry<DatatypeProperty, Integer> value2) { + if(value1.getValue() < value2.getValue()){ + return 1; + } else if(value2.getValue() < value1.getValue()){ + return -1; + } else { + return value1.getKey().compareTo(value2.getKey()); + } + } + }); + sortedSet.addAll(map.entrySet()); + return sortedSet; + } + + /* + * Executes a SELECT query and returns the result. + */ + private ResultSet executeQuery(String query){ + logger.info("Sending query \n {}", query); + + ExtendedQueryEngineHTTP queryExecution = new ExtendedQueryEngineHTTP(ks.getEndpoint().getURL().toString(), query); + queryExecution.setTimeout(maxExecutionTimeInSeconds * 1000); + for (String dgu : ks.getEndpoint().getDefaultGraphURIs()) { + queryExecution.addDefaultGraph(dgu); + } + for (String ngu : ks.getEndpoint().getNamedGraphURIs()) { + queryExecution.addNamedGraph(ngu); + } + ResultSet resultSet = queryExecution.execSelect(); + return resultSet; + } + +} Added: trunk/components-core/src/main/java/org/dllearner/algorithms/properties/FunctionalDataPropertyAxiomLearner.java =================================================================== --- trunk/components-core/src/main/java/org/dllearner/algorithms/properties/FunctionalDataPropertyAxiomLearner.java (rev 0) +++ trunk/components-core/src/main/java/org/dllearner/algorithms/properties/FunctionalDataPropertyAxiomLearner.java 2011-08-08 13:35:14 UTC (rev 3013) @@ -0,0 +1,171 @@ +package org.dllearner.algorithms.properties; + +import java.util.ArrayList; +import java.util.Collections; +import java.util.List; + +import org.dllearner.core.AbstractComponent; +import org.dllearner.core.AxiomLearningAlgorithm; +import org.dllearner.core.ComponentAnn; +import org.dllearner.core.ComponentInitException; +import org.dllearner.core.EvaluatedAxiom; +import org.dllearner.core.config.ConfigOption; +import org.dllearner.core.config.DataPropertyEditor; +import org.dllearner.core.config.IntegerEditor; +import org.dllearner.core.configurators.Configurator; +import org.dllearner.core.owl.Axiom; +import org.dllearner.core.owl.DatatypeProperty; +import org.dllearner.core.owl.FunctionalDatatypePropertyAxiom; +import org.dllearner.kb.SparqlEndpointKS; +import org.dllearner.kb.sparql.ExtendedQueryEngineHTTP; +import org.dllearner.learningproblems.AxiomScore; +import org.dllearner.reasoning.SPARQLReasoner; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; + +import com.hp.hpl.jena.query.QuerySolution; +import com.hp.hpl.jena.query.ResultSet; +import com.hp.hpl.jena.sparql.engine.http.QueryEngineHTTP; +import com.hp.hpl.jena.vocabulary.OWL; + +@ComponentAnn(name="functional property axiom learner") +public class FunctionalDataPropertyAxiomLearner extends AbstractComponent implements AxiomLearningAlgorithm { + + private static final Logger logger = LoggerFactory.getLogger(FunctionalDataPropertyAxiomLearner.class); + + @ConfigOption(name="propertyToDescribe", description="", propertyEditorClass=DataPropertyEditor.class) + private DatatypeProperty propertyToDescribe; + @ConfigOption(name="maxExecutionTimeInSeconds", description="", propertyEditorClass=IntegerEditor.class) + private int maxExecutionTimeInSeconds = 10; + @ConfigOption(name="maxFetchedRows", description="The maximum number of rows fetched from the endpoint to approximate the result.", propertyEditorClass=IntegerEditor.class) + private int maxFetchedRows = 0; + + private SPARQLReasoner reasoner; + private SparqlEndpointKS ks; + + private List<EvaluatedAxiom> currentlyBestAxioms; + private long startTime; + private int fetchedRows; + + + public FunctionalDataPropertyAxiomLearner(SparqlEndpointKS ks){ + this.ks = ks; + } + + public int getMaxExecutionTimeInSeconds() { + return maxExecutionTimeInSeconds; + } + + public void setMaxExecutionTimeInSeconds(int maxExecutionTimeInSeconds) { + this.maxExecutionTimeInSeconds = maxExecutionTimeInSeconds; + } + + public DatatypeProperty getPropertyToDescribe() { + return propertyToDescribe; + } + + public void setPropertyToDescribe(DatatypeProperty propertyToDescribe) { + this.propertyToDescribe = propertyToDescribe; + } + + public int getMaxFetchedRows() { + return maxFetchedRows; + } + + public void setMaxFetchedRows(int maxFetchedRows) { + this.maxFetchedRows = maxFetchedRows; + } + + @Override + public void start() { + logger.info("Start learning..."); + startTime = System.currentTimeMillis(); + fetchedRows = 0; + currentlyBestAxioms = new ArrayList<EvaluatedAxiom>(); + + //check if property is already declared as symmetric in knowledge base + String query = String.format("ASK {<%s> a <%s>}", propertyToDescribe, OWL.FunctionalProperty.getURI()); + boolean declaredAsFunctional = executeAskQuery(query); + if(declaredAsFunctional) { + logger.info("Property is already declared as functional in knowledge base."); + } + + //get number of instances of s with <s p o> + query = String.format("SELECT (COUNT(DISTINCT ?s)) AS ?all WHERE {?s <%s> ?o.}", propertyToDescribe.getName()); + ResultSet rs = executeQuery(query); + QuerySolution qs; + int all = 1; + while(rs.hasNext()){ + qs = rs.next(); + all = qs.getLiteral("all").getInt(); + } + //get number of instances of s with <s p o> <s p o1> where o != o1 + query = "SELECT (COUNT(DISTINCT ?s)) AS ?notfunctional WHERE {?s <%s> ?o. ?s <%s> ?o1. FILTER(?o != ?o1) }"; + query = query.replace("%s", propertyToDescribe.getURI().toString()); + rs = executeQuery(query); + int notFunctional = 1; + while(rs.hasNext()){ + qs = rs.next(); + notFunctional = qs.getLiteral("notfunctional").getInt(); + } + if(all > 0){ + double frac = (all - notFunctional) / (double)all; + currentlyBestAxioms.add(new EvaluatedAxiom(new FunctionalDatatypePropertyAxiom(propertyToDescribe), new AxiomScore(frac))); + } + + logger.info("...finished in {}ms.", (System.currentTimeMillis()-startTime)); + } + + @Override + public List<Axiom> getCurrentlyBestAxioms(int nrOfAxioms) { + return currentlyBestAxioms.isEmpty() ? Collections.<Axiom>emptyList() : Collections.singletonList(currentlyBestAxioms.get(0).getAxiom()); + } + + @Override + public List<EvaluatedAxiom> getCurrentlyBestEvaluatedAxioms(int nrOfAxioms) { + return currentlyBestAxioms; + } + + @Override + public Configurator getConfigurator() { + // TODO Auto-generated method stub + return null; + } + + @Override + public void init() throws ComponentInitException { + reasoner = new SPARQLReasoner(ks); + } + + private boolean executeAskQuery(String query){ + logger.info("Sending query \n {}", query); + + QueryEngineHTTP queryExecution = new QueryEngineHTTP(ks.getEndpoint().getURL().toString(), query); + for (String dgu : ks.getEndpoint().getDefaultGraphURIs()) { + queryExecution.addDefaultGraph(dgu); + } + for (String ngu : ks.getEndpoint().getNamedGraphURIs()) { + queryExecution.addNamedGraph(ngu); + } + boolean result = queryExecution.execAsk(); + return result; + } + + /* + * Executes a SELECT query and returns the result. + */ + private ResultSet executeQuery(String query){ + logger.info("Sending query \n {}", query); + + ExtendedQueryEngineHTTP queryExecution = new ExtendedQueryEngineHTTP(ks.getEndpoint().getURL().toString(), query); + queryExecution.setTimeout(maxExecutionTimeInSeconds * 1000); + for (String dgu : ks.getEndpoint().getDefaultGraphURIs()) { + queryExecution.addDefaultGraph(dgu); + } + for (String ngu : ks.getEndpoint().getNamedGraphURIs()) { + queryExecution.addNamedGraph(ngu); + } + ResultSet resultSet = queryExecution.execSelect(); + return resultSet; + } +} Modified: trunk/components-core/src/main/java/org/dllearner/algorithms/properties/PropertyDomainAxiomLearner.java =================================================================== --- trunk/components-core/src/main/java/org/dllearner/algorithms/properties/PropertyDomainAxiomLearner.java 2011-08-08 06:59:56 UTC (rev 3012) +++ trunk/components-core/src/main/java/org/dllearner/algorithms/properties/PropertyDomainAxiomLearner.java 2011-08-08 13:35:14 UTC (rev 3013) @@ -96,7 +96,7 @@ currentlyBestAxioms = new ArrayList<EvaluatedAxiom>(); //get existing domains Description existingDomain = reasoner.getDomain(propertyToDescribe); - logger.debug("Existing domain: " + existingDomain); + logger.info("Existing domain: " + existingDomain); //get subjects with types Map<Individual, Set<NamedClass>> individual2Types = new HashMap<Individual, Set<NamedClass>>(); Added: trunk/components-core/src/main/java/org/dllearner/algorithms/properties/SubDataPropertyOfAxiomLearner.java =================================================================== --- trunk/components-core/src/main/java/org/dllearner/algorithms/properties/SubDataPropertyOfAxiomLearner.java (rev 0) +++ trunk/components-core/src/main/java/org/dllearner/algorithms/properties/SubDataPropertyOfAxiomLearner.java 2011-08-08 13:35:14 UTC (rev 3013) @@ -0,0 +1,229 @@ +package org.dllearner.algorithms.properties; + +import java.util.ArrayList; +import java.util.Comparator; +import java.util.HashMap; +import java.util.Iterator; +import java.util.List; +import java.util.Map; +import java.util.Map.Entry; +import java.util.SortedSet; +import java.util.TreeSet; + +import org.dllearner.core.AbstractComponent; +import org.dllearner.core.AxiomLearningAlgorithm; +import org.dllearner.core.ComponentAnn; +import org.dllearner.core.ComponentInitException; +import org.dllearner.core.EvaluatedAxiom; +import org.dllearner.core.config.ConfigOption; +import org.dllearner.core.config.DataPropertyEditor; +import org.dllearner.core.config.IntegerEditor; +import org.dllearner.core.configurators.Configurator; +import org.dllearner.core.owl.Axiom; +import org.dllearner.core.owl.DatatypeProperty; +import org.dllearner.core.owl.SubDatatypePropertyAxiom; +import org.dllearner.kb.SparqlEndpointKS; +import org.dllearner.kb.sparql.ExtendedQueryEngineHTTP; +import org.dllearner.learningproblems.AxiomScore; +import org.dllearner.reasoning.SPARQLReasoner; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; + +import com.hp.hpl.jena.query.QuerySolution; +import com.hp.hpl.jena.query.ResultSet; + +@ComponentAnn(name="subPropertyOf learner") +public class SubDataPropertyOfAxiomLearner extends AbstractComponent implements AxiomLearningAlgorithm { + + private static final Logger logger = LoggerFactory.getLogger(PropertyDomainAxiomLearner.class); + + @ConfigOption(name="propertyToDescribe", description="", propertyEditorClass=DataPropertyEditor.class) + private DatatypeProperty propertyToDescribe; + @ConfigOption(name="maxExecutionTimeInSeconds", description="", propertyEditorClass=IntegerEditor.class) + private int maxExecutionTimeInSeconds = 10; + @ConfigOption(name="maxFetchedRows", description="The maximum number of rows fetched from the endpoint to approximate the result.", propertyEditorClass=IntegerEditor.class) + private int maxFetchedRows = 0; + + private SPARQLReasoner reasoner; + private SparqlEndpointKS ks; + + private List<EvaluatedAxiom> currentlyBestAxioms; + private long startTime; + private int fetchedRows; + + + public SubDataPropertyOfAxiomLearner(SparqlEndpointKS ks){ + this.ks = ks; + } + + public int getMaxExecutionTimeInSeconds() { + return maxExecutionTimeInSeconds; + } + + public void setMaxExecutionTimeInSeconds(int maxExecutionTimeInSeconds) { + this.maxExecutionTimeInSeconds = maxExecutionTimeInSeconds; + } + + public DatatypeProperty getPropertyToDescribe() { + return propertyToDescribe; + } + + public void setPropertyToDescribe(DatatypeProperty propertyToDescribe) { + this.propertyToDescribe = propertyToDescribe; + } + + public int getMaxFetchedRows() { + return maxFetchedRows; + } + + public void setMaxFetchedRows(int maxFetchedRows) { + this.maxFetchedRows = maxFetchedRows; + } + + @Override + public void start() { + logger.info("Start learning..."); + startTime = System.currentTimeMillis(); + fetchedRows = 0; + currentlyBestAxioms = new ArrayList<EvaluatedAxiom>(); + //get existing super properties + SortedSet<DatatypeProperty> existingSuperProperties = reasoner.getSuperProperties(propertyToDescribe); + logger.debug("Existing super properties: " + existingSuperProperties); + + //get subjects with types + int limit = 1000; + int offset = 0; + String queryTemplate = "SELECT ?p COUNT(?s) AS ?count WHERE {?s ?p ?o." + + "{SELECT ?s ?o WHERE {?s <%s> ?o.} LIMIT %d OFFSET %d}" + + "}"; + String query; + Map<DatatypeProperty, Integer> result = new HashMap<DatatypeProperty, Integer>(); + DatatypeProperty prop; + Integer oldCnt; + boolean repeat = true; + + while(!terminationCriteriaSatisfied() && repeat){ + query = String.format(queryTemplate, propertyToDescribe, limit, offset); + ResultSet rs = executeQuery(query); + QuerySolution qs; + repeat = false; + while(rs.hasNext()){ + qs = rs.next(); + prop = new DatatypeProperty(qs.getResource("p").getURI()); + int newCnt = qs.getLiteral("count").getInt(); + oldCnt = result.get(prop); + if(oldCnt == null){ + oldCnt = Integer.valueOf(newCnt); + } + result.put(prop, oldCnt); + qs.getLiteral("count").getInt(); + repeat = true; + } + if(!result.isEmpty()){ + currentlyBestAxioms = buildAxioms(result); + offset += 1000; + } + } + + logger.info("...finished in {}ms.", (System.currentTimeMillis()-startTime)); + } + + @Override + public List<Axiom> getCurrentlyBestAxioms(int nrOfAxioms) { + List<Axiom> bestAxioms = new ArrayList<Axiom>(); + + Iterator<EvaluatedAxiom> it = currentlyBestAxioms.iterator(); + while(bestAxioms.size() < nrOfAxioms && it.hasNext()){ + bestAxioms.add(it.next().getAxiom()); + } + + return bestAxioms; + } + + @Override + public List<EvaluatedAxiom> getCurrentlyBestEvaluatedAxioms(int nrOfAxioms) { + int max = Math.min(currentlyBestAxioms.size(), nrOfAxioms); + + List<EvaluatedAxiom> bestAxioms = currentlyBestAxioms.subList(0, max); + + return bestAxioms; + } + + @Override + public Configurator getConfigurator() { + // TODO Auto-generated method stub + return null; + } + + @Override + public void init() throws ComponentInitException { + reasoner = new SPARQLReasoner(ks); + + } + + private boolean terminationCriteriaSatisfied(){ + boolean timeLimitExceeded = maxExecutionTimeInSeconds == 0 ? false : (System.currentTimeMillis() - startTime) >= maxExecutionTimeInSeconds * 1000; + boolean resultLimitExceeded = maxFetchedRows == 0 ? false : fetchedRows >= maxFetchedRows; + return timeLimitExceeded || resultLimitExceeded; + } + + private List<EvaluatedAxiom> buildAxioms(Map<DatatypeProperty, Integer> property2Count){ + List<EvaluatedAxiom> axioms = new ArrayList<EvaluatedAxiom>(); + Integer all = property2Count.get(propertyToDescribe); + property2Count.remove(propertyToDescribe); + + EvaluatedAxiom evalAxiom; + for(Entry<DatatypeProperty, Integer> entry : sortByValues(property2Count)){ + evalAxiom = new EvaluatedAxiom(new SubDatatypePropertyAxiom(propertyToDescribe, entry.getKey()), + new AxiomScore(entry.getValue() / (double)all)); + axioms.add(evalAxiom); + } + + property2Count.put(propertyToDescribe, all); + return axioms; + } + + /* + * Returns the entries of the map sorted by value. + */ + private SortedSet<Entry<DatatypeProperty, Integer>> sortByValues(Map<DatatypeProperty, Integer> map){ + SortedSet<Entry<DatatypeProperty, Integer>> sortedSet = new TreeSet<Map.Entry<DatatypeProperty,Integer>>(new Comparator<Entry<DatatypeProperty, Integer>>() { + + @Override + public int compare(Entry<DatatypeProperty, Integer> value1, Entry<DatatypeProperty, Integer> value2) { + if(value1.getValue() < value2.getValue()){ + return 1; + } else if(value2.getValue() < value1.getValue()){ + return -1; + } else { + return value1.getKey().compareTo(value2.getKey()); + } + } + }); + sortedSet.addAll(map.entrySet()); + return sortedSet; + } + + private long getRemainingMaxExecutionTime(){ + return (maxExecutionTimeInSeconds == 0) ? 0 : Math.max(1, (maxExecutionTimeInSeconds * 1000)-(System.currentTimeMillis()-startTime)); + } + + /* + * Executes a SELECT query and returns the result. + */ + private ResultSet executeQuery(String query){ + logger.info("Sending query \n {}", query); + + ExtendedQueryEngineHTTP queryExecution = new ExtendedQueryEngineHTTP(ks.getEndpoint().getURL().toString(), query); + queryExecution.setTimeout(getRemainingMaxExecutionTime()); + for (String dgu : ks.getEndpoint().getDefaultGraphURIs()) { + queryExecution.addDefaultGraph(dgu); + } + for (String ngu : ks.getEndpoint().getNamedGraphURIs()) { + queryExecution.addNamedGraph(ngu); + } + ResultSet resultSet = queryExecution.execSelect(); + return resultSet; + } + +} Modified: trunk/components-core/src/main/java/org/dllearner/algorithms/properties/SubPropertyOfAxiomLearner.java =================================================================== --- trunk/components-core/src/main/java/org/dllearner/algorithms/properties/SubPropertyOfAxiomLearner.java 2011-08-08 06:59:56 UTC (rev 3012) +++ trunk/components-core/src/main/java/org/dllearner/algorithms/properties/SubPropertyOfAxiomLearner.java 2011-08-08 13:35:14 UTC (rev 3013) @@ -55,6 +55,7 @@ private long startTime; private int fetchedRows; + public SubPropertyOfAxiomLearner(SparqlEndpointKS ks){ this.ks = ks; } @@ -207,6 +208,10 @@ return sortedSet; } + private long getRemainingMaxExecutionTime(){ + return (maxExecutionTimeInSeconds == 0) ? 0 : Math.max(1, (maxExecutionTimeInSeconds * 1000)-(System.currentTimeMillis()-startTime)); + } + /* * Executes a SELECT query and returns the result. */ @@ -214,7 +219,7 @@ logger.info("Sending query \n {}", query); ExtendedQueryEngineHTTP queryExecution = new ExtendedQueryEngineHTTP(ks.getEndpoint().getURL().toString(), query); - queryExecution.setTimeout(maxExecutionTimeInSeconds * 1000); + queryExecution.setTimeout(getRemainingMaxExecutionTime()); for (String dgu : ks.getEndpoint().getDefaultGraphURIs()) { queryExecution.addDefaultGraph(dgu); } Added: trunk/components-core/src/main/java/org/dllearner/core/config/DataPropertyEditor.java =================================================================== --- trunk/components-core/src/main/java/org/dllearner/core/config/DataPropertyEditor.java (rev 0) +++ trunk/components-core/src/main/java/org/dllearner/core/config/DataPropertyEditor.java 2011-08-08 13:35:14 UTC (rev 3013) @@ -0,0 +1,90 @@ +package org.dllearner.core.config; + +import java.awt.Component; +import java.awt.Graphics; +import java.awt.Rectangle; +import java.beans.PropertyChangeListener; +import java.beans.PropertyEditor; + +import org.dllearner.core.owl.DatatypeProperty; + +/** + * Created by IntelliJ IDEA. + * User: Chris + * Date: 7/26/11 + * Time: 9:42 PM + * <p/> + * Basic Property Editor for the Object Property DL-Learner class. Doesn't have GUI support yet but we could add that later if we wanted. + */ +public class DataPropertyEditor implements PropertyEditor { + + + private DatatypeProperty value; + + @Override + public void setValue(Object value) { + this.value = (DatatypeProperty) value; + } + + @Override + public Object getValue() { + return value; + } + + @Override + public boolean isPaintable() { + /** Not right now, we're doing non gui work */ + return false; + } + + @Override + public void paintValue(Graphics gfx, Rectangle box) { + + } + + @Override + public String getJavaInitializationString() { + /** This returns the value needed to reconstitute the object from a string */ + return value.getName(); + } + + @Override + public String getAsText() { + /** Get the text value of this object - for displaying in GUIS, etc */ + return value.getName(); + } + + @Override + public void setAsText(String text) throws IllegalArgumentException { + value = new DatatypeProperty(text); + } + + @Override + public String[] getTags() { + /** If there was a known set of values it had to have, we could add that list here */ + return new String[0]; + } + + @Override + public Component getCustomEditor() { + /** GUI stuff, if you wanted to edit it a custom way */ + return null; + } + + @Override + public boolean supportsCustomEditor() { + /** We don't support this right now, but maybe later */ + return false; + + } + + @Override + public void addPropertyChangeListener(PropertyChangeListener listener) { + /** More gui stuff, we don't need this for our basic example */ + } + + @Override + public void removePropertyChangeListener(PropertyChangeListener listener) { + /** More gui stuff, we don't need this for our basic example */ + } +} Added: trunk/components-core/src/main/java/org/dllearner/core/owl/DisjointDatatypePropertyAxiom.java =================================================================== --- trunk/components-core/src/main/java/org/dllearner/core/owl/DisjointDatatypePropertyAxiom.java (rev 0) +++ trunk/components-core/src/main/java/org/dllearner/core/owl/DisjointDatatypePropertyAxiom.java 2011-08-08 13:35:14 UTC (rev 3013) @@ -0,0 +1,55 @@ +package org.dllearner.core.owl; + +import java.util.Map; + +public class DisjointDatatypePropertyAxiom extends PropertyAxiom { + + /** + * + */ + private static final long serialVersionUID = -1085651734702155330L; + private DatatypeProperty role; + private DatatypeProperty disjointRole; + + public DisjointDatatypePropertyAxiom(DatatypeProperty role, DatatypeProperty disjointRole) { + this.role = role; + this.disjointRole = disjointRole; + } + + public DatatypeProperty getRole() { + return role; + } + + public DatatypeProperty getDisjointRole() { + return disjointRole; + } + + public int getLength() { + return 1 + role.getLength() + disjointRole.getLength(); + } + + public String toString(String baseURI, Map<String,String> prefixes) { + return "DisjointObjectProperties(" + role.toString(baseURI, prefixes) + "," + disjointRole.toString(baseURI, prefixes) + ")"; + } + + public String toKBSyntaxString(String baseURI, Map<String,String> prefixes) { + return "DisjointObjectProperties(" + role.toKBSyntaxString(baseURI, prefixes) + "," + disjointRole.toKBSyntaxString(baseURI, prefixes) + ")"; + } + + @Override + public void accept(AxiomVisitor visitor) { + visitor.visit(this); + } + + public void accept(KBElementVisitor visitor) { + visitor.visit(this); + } + + /* (non-Javadoc) + * @see org.dllearner.core.owl.KBElement#toManchesterSyntaxString(java.lang.String, java.util.Map) + */ + @Override + public String toManchesterSyntaxString(String baseURI, Map<String, String> prefixes) { + return role.toString(baseURI, prefixes) + " DisjointWith: " + disjointRole.toString(baseURI, prefixes); + } +} Added: tr... [truncated message content] |