来自Apache Jena框架的推理示例的问题 [英] Problems with inference examples from Apache Jena framework

查看:115
本文介绍了来自Apache Jena框架的推理示例的问题的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我有一个严重的问题,无法启动和运行任何推理程序. 还有文档中的示例: https://jena.apache.org/documentation/inference/ 在这里不起作用. 我将示例转移到了单元测试中,以便可以更轻松地重现该问题.

I have a serious problem to get any reasoner up and running. Also the examples from the documentation: https://jena.apache.org/documentation/inference/ does not work here. I transferred the example into a unit test, so that the problem might be easier reproduced.

推理是否仅限于某些环境,例如空间JDK等,还是我出了点问题?

Is reasoning limited to certain environment like a spatial JDK or so on, or am i getting something wrong?

谢谢

这里是示例代码(作为Java单元测试):

Here the example code (as java unit test):

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:前缀不会扩展为您认为的那样.我将您的规则字符串修改为

The prefix eg: isn't what you think it is:

The eg: prefix in the rules doesn't expand to what you think it does. I modified your rules string to

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

,以便rule2始终将三元组 urn:ex:a例如:foo urn:ex:b 插入到图形中.然后,您的测试输出包括:

so that rule2 will always insert the triple urn:ex:a eg:foo urn:ex:b into the graph. Then, the output from your tests includes:

[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/的缩写.如果使用String NS = "urn:x-hp:eg/";相应地更改NS字符串,则派生测试将通过.

The first line shows the triple that my rule2 inserted, whereas the second uses the prefix you entered by hand. We see that the eg: prefix is short for urn:x-hp:eg/. If you change your NS string accordingly, with String NS = "urn:x-hp:eg/";, then your derivations test will pass.

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

The subProperty test fails for two reasons. First, it's checking in the wrong model.

您正在使用A.getProperty(q)进行检查:

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

A是为模型model创建的资源,而不是为模型inf创建的资源,因此,当您请求A.getProperty(q)时,实际上是在向model请求该语句,因此您不会看不到inf中的推论.您可以使用inModelinf中获取A,以便getProperty在正确的模型中显示:

A is a resource that you created for the the model model, not the model inf, so when you ask for A.getProperty(q), it's actually asking model for the statement, so you won't see the inferences in inf. You can use inModel to get A "in inf" so that getProperty looks in the right model:

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

或者,您也可以直接询问inf它是否包含形式为A q <something>的三元组:

Alternatively, you could also ask inf directly whether it contains a triple of the form A q <something>:

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

或者您可以列举所有此类语句:

Or you could enumerate all such statements:

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

您也需要RDFS推理

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

You need RDFS reasoning too

Even if you're querying the right model, your inference model still needs to do RDFS reasoning as well as your custom rule that makes the property p transitive. To do that, we can pull the rules out from an RDFS reasoner, add your rule to that a copy of that list, and then create a custom reasoner with the new list of rules:

// 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<Rule> 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 );

完整结果

这是修改后的代码,所有代码在一起,便于复制和粘贴.所有测试都通过了.

The complete result

Here's the modified code, all together for easy copying and pasting. All the tests pass.

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<Rule> 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<Derivation> 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());
        }
    }
}

这篇关于来自Apache Jena框架的推理示例的问题的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆