2014-04-30 64 views
0

這是我寫的代碼,但新的內置似乎並沒有工作。我得到的錯誤:在耶拿定製內置

Exception in thread "main" com.hp.hpl.jena.reasoner.rulesys.impl.LPRuleSyntaxException: Syntax error in backward rule: matematica Unknown builtin operation mysum

任何人都可以告訴我錯誤在哪裏?這裏是我的代碼:

package JenaRules; 

import java.io.BufferedReader; 
import java.io.ByteArrayInputStream; 
import java.io.IOException; 
import java.io.InputStreamReader; 
import java.util.Arrays; 
import java.util.List; 

import org.semanticweb.owlapi.model.OWLOntologyCreationException; 
import org.semanticweb.owlapi.model.OWLOntologyStorageException; 

import com.hp.hpl.jena.graph.Node; 
import com.hp.hpl.jena.query.Query; 
import com.hp.hpl.jena.query.QueryExecution; 
import com.hp.hpl.jena.query.QueryExecutionFactory; 
import com.hp.hpl.jena.query.QueryFactory; 
import com.hp.hpl.jena.query.ResultSet; 
import com.hp.hpl.jena.query.ResultSetFormatter; 
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.Resource; 
import com.hp.hpl.jena.reasoner.Reasoner; 
import com.hp.hpl.jena.reasoner.rulesys.*; 
import com.hp.hpl.jena.reasoner.rulesys.builtins.BaseBuiltin; 
import com.hp.hpl.jena.util.FileManager; 
import com.hp.hpl.jena.vocabulary.RDFS; 
import com.hp.hpl.jena.vocabulary.ReasonerVocabulary; 

public class RulesOntology_MT { 

    public static void main(String[] args) throws OWLOntologyStorageException, 
    OWLOntologyCreationException, IOException { 

     BuiltinRegistry.theRegistry.register(new BaseBuiltin() { 
      @Override 
      public String getName() { 
        return "mysum"; 
       } 
      @Override 
       public int getArgLength() { 
        return 2; 
       } 
      @Override 
       public boolean bodyCall(Node[] args, int length, RuleContext context) { 
        checkArgs(length, context); 
        BindingEnvironment env = context.getEnv(); 
        Node n1 = getArg(0, args, context); 
        Node n2 = getArg(1, args, context); 
        if (n1.isLiteral() && n2.isLiteral()) { 
         Object v1 = n1.getLiteralValue(); 
         Object v2 = n2.getLiteralValue(); 
         Node sum = null; 
         if (v1 instanceof Number && v2 instanceof Number) { 
          Number nv1 = (Number)v1; 
          Number nv2 = (Number)v2; 
          int sumInt = nv1.intValue()+nv2.intValue(); 
          sum = Util.makeIntNode(sumInt); 
          return env.bind(args[2], sum); 
         } 
        } 
        return false; 
       } 

     }); 

     // NON SERVE 

     //  final String exampleRuleString2 = 
     //    "[mat1: equal(?s ?p)\n\t-> print(?s ?p ?o),\n\t (?s ?p ?o)\n]"+ 
     //      ""; 

     final String exampleRuleString =  
       "[matematica:"+ 
         "(?p http://www.semanticweb.org/prova_rules_M#totale_crediti ?x)"+ 
         " -> " + 
         "(?p rdf:type http://www.semanticweb.org/prova_rules_M#:Persona)"+ 
         "(?e rdf:type http://www.semanticweb.org/prova_rules_M#:Esame)"+ 
         "(?p http://www.semanticweb.org/prova_rules_M#:haSostenutoEsameDi ?e)"+ 
         "(?e http://www.semanticweb.org/prova_rules_M/persona#crediti_esame ?cr)"+ 
         "mysum(?cr,2)"+ 
         "]"; 

     System.out.println(exampleRuleString); 

     /* I tend to use a fairly verbose syntax for parsing out my rules when I construct them 
     * from a string. You can read them from whatever other sources. 
     */ 
     final List<Rule> rules; 
     try(final BufferedReader src = new BufferedReader(new InputStreamReader(new ByteArrayInputStream(exampleRuleString.getBytes())))) { 
      rules = Rule.parseRules(Rule.rulesParserFromReader(src)); 
     } 


     /* Construct a reasoner and associate the rules with it */ 
     // create an empty non-inferencing model 

     GenericRuleReasoner reasoner = (GenericRuleReasoner) GenericRuleReasonerFactory.theInstance().create(null); 
     reasoner.setRules(rules); 


     /* Create & Prepare the InfModel. If you don't call prepare, then 
     * rule firings and inference may be deferred until you query the 
     * model rather than happening at insertion. This can make you think 
     * that your Builtin is not working, when it is. 
     */ 

     InfModel infModel = ModelFactory.createInfModel(reasoner, ModelFactory.createDefaultModel()); 
     infModel.prepare(); 
     infModel.createResource(RDFS.Class); 

     //write down the result in RDFXML form 
     infModel.write(System.out); 

    } 
} 
+1

「*但新的內置似乎沒有工作,它不被認可*」>我不明白你的問題的描述。你看到什麼問題?編譯錯誤?運行時錯誤?意外的輸出? –

+0

我的錯誤是: 線程「main」中的異常com.hp.hpl.jena.reasoner.rulesys.impl.LPRuleSyntaxException:向後規則中的語法錯誤:matematica 未知的內置操作mysum。 我不知道我可以如何設置推理器,讓它識別新的內置。 – user3563844

回答

0

使用您提供的代碼,和Apache耶拿2.11.1,我不能複製你所得到的例外。請注意,當你致電BuiltinRegistry.theRegistry.register(...)時,你的告訴推理者,內在的存在。

解決方案

例外,你越來越可能是因爲,在你實際代碼,你是不是叫Rule.parseRules(Rule.rulesParserFromReader(src));在調用BuiltinRegistry.theRegistry.register(...),所以只要規則解析器而言,您正在使用不存在的Builtin。要解決它,只需在解析規則之前先撥打register即可。提供的玩具示例沒有這個問題。使用

提供

我也注意到,所提供的代碼示例不包括任何會真正刺激的規則火的例子,所以,代替infModel.createResource(RDFS.Class);,我加了以下幾行:

final Resource s = infModel.createResource(); 
final Property p = infModel.createProperty("http://www.semanticweb.org/prova_rules_M#totale_crediti"); 
final Resource o = infModel.createResource(); 
infModel.add(s,p,o); 

這刺激了規則火災,並導致以下異常跟蹤:

com.hp.hpl.jena.reasoner.rulesys.BuiltinException: Error in clause of rule (matematica) mysum: builtin mysum not usable in rule heads 
    at com.hp.hpl.jena.reasoner.rulesys.builtins.BaseBuiltin.headAction(BaseBuiltin.java:86) 
    at com.hp.hpl.jena.reasoner.rulesys.impl.RETEConflictSet.execute(RETEConflictSet.java:184) 
    at com.hp.hpl.jena.reasoner.rulesys.impl.RETEConflictSet.add(RETEConflictSet.java:81) 
    at com.hp.hpl.jena.reasoner.rulesys.impl.RETEEngine.requestRuleFiring(RETEEngine.java:249) 
    at com.hp.hpl.jena.reasoner.rulesys.impl.RETETerminal.fire(RETETerminal.java:80) 
    at com.hp.hpl.jena.reasoner.rulesys.impl.RETEClauseFilter.fire(RETEClauseFilter.java:227) 
    at com.hp.hpl.jena.reasoner.rulesys.impl.RETEEngine.inject(RETEEngine.java:469) 
    at com.hp.hpl.jena.reasoner.rulesys.impl.RETEEngine.runAll(RETEEngine.java:451) 
    at com.hp.hpl.jena.reasoner.rulesys.impl.RETEEngine.add(RETEEngine.java:174) 
    at com.hp.hpl.jena.reasoner.rulesys.FBRuleInfGraph.performAdd(FBRuleInfGraph.java:654) 
    at com.hp.hpl.jena.graph.impl.GraphBase.add(GraphBase.java:202) 
    at com.hp.hpl.jena.rdf.model.impl.ModelCom.add(ModelCom.java:1138) 
    at SO.test(SO.java:108) 

作爲說明:我的測試課程是SO.java,第108行是我們所說的infModel.add(s,p,o)

我得到的異常與您遇到的異常不同,但值得解釋。您提供的實施實施Builtin#bodyCall(...),但不是Builtin#headAction(...)。我們可以看到這個例外是從BaseBuiltin#headAction(...)引發的。此默認行爲假定您沒有實現該方法,因爲您的Builtin不支持它。在玩具問題中,這是正確的行爲,因爲示例實施不能在規則頭部使用

+1

有趣的是「**後向規則**中的語法錯誤:matematica未知的內置操作mysum」。這個問題不是寫在規則上的規則(身體裏有一個東西,頭上五個東西)是一個前向規則嗎? –

+0

你是對的。所提供的玩具示例似乎並不反映所討論的實際規則。 –

+0

大家好! 非常感謝您的貢獻。感謝你解決了這個問題。 我已經構建了一個定製的內置! – user3563844