Apache Jena框架的推理示例存在问题

我有一个严重的问题,让任何推理器运行起来。 此外,文档中的示例: https : //jena.apache.org/documentation/inference/在此处不起作用。 我将示例转移到unit testing中,以便可以更容易地再现问题。

推理仅限于某些环境,如空间JDK等,或者我遇到了什么问题?

谢谢

这里的示例代码(作为javaunit testing):

import static org.junit.Assert.assertNotNull; import java.io.PrintWriter; import java.util.Iterator; import org.junit.Before; import org.junit.Test; import com.hp.hpl.jena.rdf.model.InfModel; import com.hp.hpl.jena.rdf.model.Model; import com.hp.hpl.jena.rdf.model.ModelFactory; import com.hp.hpl.jena.rdf.model.Property; import com.hp.hpl.jena.rdf.model.Resource; import com.hp.hpl.jena.rdf.model.Statement; import com.hp.hpl.jena.rdf.model.StmtIterator; import com.hp.hpl.jena.reasoner.Derivation; import com.hp.hpl.jena.reasoner.rulesys.GenericRuleReasoner; import com.hp.hpl.jena.reasoner.rulesys.Rule; import com.hp.hpl.jena.vocabulary.RDFS; public class ReasonerTest { String NS = "urn:x-hp-jena:eg/"; // Build a trivial example data set Model model = ModelFactory.createDefaultModel(); InfModel inf; Resource A = model.createResource(NS + "A"); Resource B = model.createResource(NS + "B"); Resource C = model.createResource(NS + "C"); Resource D = model.createResource(NS + "D"); Property p = model.createProperty(NS, "p"); Property q = model.createProperty(NS, "q"); @Before public void init() { // Some small examples (subProperty) model.add(p, RDFS.subPropertyOf, q); model.createResource(NS + "A").addProperty(p, "foo"); String rules = "[rule1: (?a eg:p ?b) (?b eg:p ?c) -> (?a eg:p ?c)]"; GenericRuleReasoner reasoner = new GenericRuleReasoner(Rule.parseRules(rules)); reasoner.setDerivationLogging(true); inf = ModelFactory.createInfModel(reasoner, model); // Derivations A.addProperty(p, B); B.addProperty(p, C); C.addProperty(p, D); } @Test public void subProperty() { Statement statement = A.getProperty(q); System.out.println("Statement: " + statement); assertNotNull(statement); } @Test public void derivations() { String trace = null; PrintWriter out = new PrintWriter(System.out); for (StmtIterator i = inf.listStatements(A, p, D); i.hasNext(); ) { Statement s = i.nextStatement(); System.out.println("Statement is " + s); for (Iterator id = inf.getDerivation(s); id.hasNext(); ) { Derivation deriv = (Derivation) id.next(); deriv.printTrace(out, true); trace += deriv.toString(); } } out.flush(); assertNotNull(trace); } @Test public void listStatements() { StmtIterator stmtIterator = inf.listStatements(); while(stmtIterator.hasNext()) { System.out.println(stmtIterator.nextStatement()); } } } 

前缀例如:不是你认为的那样:

规则中的eg:前缀不会扩展到您的想法。 我将你的规则字符串修改为

 String rules = "[rule1: (?a eg:p ?b) (?b eg:p ?c) -> (?a eg:p ?c)] [rule2: -> ( eg:foo )]"; 

因此rule2将始终插入三元组:ex:a eg:foo urn:ex:b into the graph。 然后,测试的输出包括:

 [urn:ex:a, urn:x-hp:eg/foo, urn:ex:b] [urn:x-hp-jena:eg/C, urn:x-hp-jena:eg/p, urn:x-hp-jena:eg/D] 

第一行显示我的rule2插入的三元组,而第二行使用您手动输入的前缀。 我们看到eg:前缀是urn:x-hp:eg/缩写urn:x-hp:eg/ 。 如果相应地更改了NS字符串,则使用String NS = "urn:x-hp:eg/"; ,那么你的推导测试将通过。

你需要问正确的模型

subProperty测试失败有两个原因。 首先,它正在检查错误的模型。

你正在检查A.getProperty(q)

 Statement statement = A.getProperty(q); System.out.println("Statement: " + statement); assertNotNull(statement); 

A是您为模型model创建的资源,而不是模型inf ,因此当您要求A.getProperty(q) ,它实际上是在询问model的语句,因此您不会在inf看到推论。 您可以使用inModel获取A “in inf ”,以便getProperty查找正确的模型:

 Statement statement = A.inModel(inf).getProperty(q); 

或者,您也可以直接询问inf是否包含A q forms的三元组:

 inf.contains( A, q, (RDFNode) null ); 

或者你可以列举所有这些陈述:

 StmtIterator stmts = inf.listStatements( A, q, (RDFNode) null ); assertTrue( stmts.hasNext() ); while ( stmts.hasNext() ) { System.out.println( "Statement: "+stmts.next() ); } 

你也需要RDFS推理

即使您正在查询正确的模型,您的推理模型仍然需要进行RDFS推理以及使属性p传递的自定义规则。 为此,我们可以从RDFS推理器中取出规则,将规则添加到该列表的副本,然后使用新的规则列表创建自定义推理器:

 // Get an RDFS reasoner GenericRuleReasoner rdfsReasoner = (GenericRuleReasoner) ReasonerRegistry.getRDFSReasoner(); // Steal its rules, and add one of our own, and create a // reasoner with these rules List customRules = new ArrayList<>( rdfsReasoner.getRules() ); String customRule = "[rule1: (?a eg:p ?b) (?b eg:p ?c) -> (?a eg:p ?c)]"; customRules.add( Rule.parseRule( customRule )); Reasoner reasoner = new GenericRuleReasoner( customRules ); 

完整的结果

这是修改后的代码,一起用于轻松复制和粘贴。 所有的测试都通过了。

 import static org.junit.Assert.assertNotNull; import static org.junit.Assert.assertTrue; import java.io.PrintWriter; import java.util.ArrayList; import java.util.Iterator; import java.util.List; import org.junit.Before; import org.junit.Test; import com.hp.hpl.jena.rdf.model.InfModel; import com.hp.hpl.jena.rdf.model.Model; import com.hp.hpl.jena.rdf.model.ModelFactory; import com.hp.hpl.jena.rdf.model.Property; import com.hp.hpl.jena.rdf.model.RDFNode; import com.hp.hpl.jena.rdf.model.Resource; import com.hp.hpl.jena.rdf.model.Statement; import com.hp.hpl.jena.rdf.model.StmtIterator; import com.hp.hpl.jena.reasoner.Derivation; import com.hp.hpl.jena.reasoner.Reasoner; import com.hp.hpl.jena.reasoner.ReasonerRegistry; import com.hp.hpl.jena.reasoner.rulesys.GenericRuleReasoner; import com.hp.hpl.jena.reasoner.rulesys.Rule; import com.hp.hpl.jena.vocabulary.RDFS; public class ReasonerTest { String NS = "urn:x-hp:eg/"; // Build a trivial example data set Model model = ModelFactory.createDefaultModel(); InfModel inf; Resource A = model.createResource(NS + "A"); Resource B = model.createResource(NS + "B"); Resource C = model.createResource(NS + "C"); Resource D = model.createResource(NS + "D"); Property p = model.createProperty(NS, "p"); Property q = model.createProperty(NS, "q"); @Before public void init() { // Some small examples (subProperty) model.add(p, RDFS.subPropertyOf, q); A.addProperty(p, "foo" ); // Get an RDFS reasoner GenericRuleReasoner rdfsReasoner = (GenericRuleReasoner) ReasonerRegistry.getRDFSReasoner(); // Steal its rules, and add one of our own, and create a // reasoner with these rules List customRules = new ArrayList<>( rdfsReasoner.getRules() ); String customRule = "[rule1: (?a eg:p ?b) (?b eg:p ?c) -> (?a eg:p ?c)]"; customRules.add( Rule.parseRule( customRule )); Reasoner reasoner = new GenericRuleReasoner( customRules ); reasoner.setDerivationLogging(true); inf = ModelFactory.createInfModel(reasoner, model); // Derivations A.addProperty(p, B); B.addProperty(p, C); C.addProperty(p, D); } @Test public void subProperty() { StmtIterator stmts = inf.listStatements( A, q, (RDFNode) null ); assertTrue( stmts.hasNext() ); while ( stmts.hasNext() ) { System.out.println( "Statement: "+stmts.next() ); } } @Test public void derivations() { String trace = null; PrintWriter out = new PrintWriter(System.out); for (StmtIterator i = inf.listStatements(A, p, D); i.hasNext(); ) { Statement s = i.nextStatement(); System.out.println("Statement is " + s); for (Iterator id = inf.getDerivation(s); id.hasNext(); ) { Derivation deriv = (Derivation) id.next(); deriv.printTrace(out, true); trace += deriv.toString(); } } out.flush(); assertNotNull(trace); } @Test public void listStatements() { StmtIterator stmtIterator = inf.listStatements(); while(stmtIterator.hasNext()) { System.out.println(stmtIterator.nextStatement()); } } }