根据文档(并使用 Jena 2.11.1 进行测试),您可以访问一个Derivation
对象,该对象将允许您创建对所发生事件的文本描述。在下面的示例中,我们检索RuleDerivation
暴露了更多关于内部状态的对象。
以下是文档示例的经过测试的实现,它以以下模型开头:
<urn:eg:C> <urn:eg:p> <urn:eg:D> .
<urn:eg:B> <urn:eg:p> <urn:eg:C> .
<urn:eg:A> <urn:eg:p> <urn:eg:B> .
...以及以下规则:
[rule1: (?a urn:eg:p ?b) (?b urn:eg:p ?c) -> (?a urn:eg:p ?c)]
...产生这个结果模型:
<urn:eg:B> <urn:eg:p> <urn:eg:D> , <urn:eg:C> .
<urn:eg:A> <urn:eg:p> <urn:eg:D> , <urn:eg:C> , <urn:eg:B> .
<urn:eg:C> <urn:eg:p> <urn:eg:D> .
这种基本的传递推理成为下面示例的核心方面。请注意,我们获得了一个实例,RuleDerivation
该实例是您最终目标的开始。
final Resource A = ResourceFactory.createResource("urn:eg:A");
final Resource B = ResourceFactory.createResource("urn:eg:B");
final Resource C = ResourceFactory.createResource("urn:eg:C");
final Resource D = ResourceFactory.createResource("urn:eg:D");
final Property p = ResourceFactory.createProperty("urn:eg:p");
final Model rawData = ModelFactory.createDefaultModel();
rawData.add(A, p, B);
rawData.add(B, p, C);
rawData.add(C, p, D);
final String rules = "[rule1: (?a urn:eg:p ?b) (?b urn:eg:p ?c) -> (?a urn:eg:p ?c)]";
final Reasoner reasoner = new GenericRuleReasoner(Rule.parseRules(rules));
reasoner.setDerivationLogging(true);
final InfModel inf = ModelFactory.createInfModel(reasoner, rawData);
final 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 (final Iterator<Derivation> id = inf.getDerivation(s); id.hasNext(); ) {
final RuleDerivation deriv = (RuleDerivation) id.next();
deriv.printTrace(out, true);
}
}
out.flush();
这个例子的输出是:
Statement is [urn:eg:A, urn:eg:p, urn:eg:D]
Rule rule1 concluded (urn:eg:A urn:eg:p urn:eg:D) <-
Rule rule1 concluded (urn:eg:A urn:eg:p urn:eg:C) <-
Fact (urn:eg:A urn:eg:p urn:eg:B)
Fact (urn:eg:B urn:eg:p urn:eg:C)
Fact (urn:eg:C urn:eg:p urn:eg:D)
编辑 - 提示
RuleDerivation#printTrace(...)
如果您正在寻找有关如何探索推导的示例,请查看内部结构。如果要将三元组(from RuleDerivation#getMatches()
)转换回语句,请使用StatementImpl#toStaetment(Triple,ModelCom)
.
EDIT2 - 完成假设您使用的是 Jena 内置的基于规则的推理器之一,以下代码将允许您探索推理器报告的一个特定推导的匹配。
final StmtIterator input = inf.listStatements(A, p, D);
assert( input.hasNext() );
final Iterator<Derivation> derivations = inf.getDerivation(input.next());
assert( null != derivations );
assert( derivations.hasNext() );
final RuleDerivation oneDerivation = (RuleDerivation) derivations.next();
final ExtendedIterator< Statement > matches =
new NiceIterator< Triple >()
.andThen( oneDerivation.getMatches().iterator())
.mapWith( new Map1< Triple, Statement >(){
@Override
public Statement map1( final Triple t )
{
/* Note that it seems that this model doesn't really mean anything. While
* the statement will be associated with the infModel, the triple that led
* to the match could have been from either the deductions graph or the
* raw graph. This does not actually add any triples to the underlying
* store.
*/
return StatementImpl.toStatement(t, (ModelCom)inf);
}});