You are viewing a plain text version of this content. The canonical link for it is here.
Posted to users@jena.apache.org by "fransworsten@googlemail.com" <fr...@googlemail.com> on 2012/05/29 19:10:15 UTC

Jena Rules: Execution order

According to the documentation "there is no guarantee of the order in 
which matching rules will fire". So is the general approach to 
instantiate two RuleReasoners when certain rules require, that other 
rules have been tested before?

For example, let's say there is rule, that adds a statement when certain 
conditions are met:

|  [rule1: (?x rdf:type :X) (?x :hasValue ?y) greaterThan(?y, 123)
      ->  (?x :hasSpecialValue ?y) ]
|

Furthermore there is a rule, that adds a different statement, when a 
resource doesn't contain a statement with the predicate 'hasSpecialValue':

|  [rule2: (?x rdf:type :X) noValue(?x, :hasSpecialValue)
      ->  (?x :hasNoSpecialValue ?y) ]
|

This rule, however, should only be executed, when the former has been 
tried. In the rules file the second rule has been placed below the first 
one, but according to the documentation this is no guarantee it won't be 
executed first.

For the example provided I could simply |noValue(?x, :hasSpecialValue)| 
with |le(?y, 123)| to get the same result. However, in my rules file 
there rules with a lot more conditions and reasoning performance 
currently not satisfying, so by adding further rules for checking 
negations, that are implied due to the absence of data (noValue), will 
probably further decrease performance.

So would it be best to use the output of RuleReasoner, that applies a 
set of basic rules, as input for another with rules based on the first set?

|   Reasoner reasoner = new GenericRuleReasoner(rules);
   Model model2 = ModelFactory.createInfModel(reasoner, model);
   Reasoner reasoner2 = new GenericRuleReasoner(rules2);
   return reasoners.createInfModel(reasoner2, model2);
|


Re: Jena Rules: Execution order

Posted by Dave Reynolds <da...@gmail.com>.
On 29/05/12 18:10, fransworsten@googlemail.com wrote:
> According to the documentation "there is no guarantee of the order in
> which matching rules will fire". So is the general approach to
> instantiate two RuleReasoners when certain rules require, that other
> rules have been tested before?
>
> For example, let's say there is rule, that adds a statement when certain
> conditions are met:
>
> | [rule1: (?x rdf:type :X) (?x :hasValue ?y) greaterThan(?y, 123)
> -> (?x :hasSpecialValue ?y) ]
> |
>
> Furthermore there is a rule, that adds a different statement, when a
> resource doesn't contain a statement with the predicate 'hasSpecialValue':
>
> | [rule2: (?x rdf:type :X) noValue(?x, :hasSpecialValue)
> -> (?x :hasNoSpecialValue ?y) ]
> |
>
> This rule, however, should only be executed, when the former has been
> tried. In the rules file the second rule has been placed below the first
> one, but according to the documentation this is no guarantee it won't be
> executed first.
>
> For the example provided I could simply |noValue(?x, :hasSpecialValue)|
> with |le(?y, 123)| to get the same result. However, in my rules file
> there rules with a lot more conditions and reasoning performance
> currently not satisfying, so by adding further rules for checking
> negations, that are implied due to the absence of data (noValue), will
> probably further decrease performance.
>
> So would it be best to use the output of RuleReasoner, that applies a
> set of basic rules, as input for another with rules based on the first set?
>
> | Reasoner reasoner = new GenericRuleReasoner(rules);
> Model model2 = ModelFactory.createInfModel(reasoner, model);
> Reasoner reasoner2 = new GenericRuleReasoner(rules2);
> return reasoners.createInfModel(reasoner2, model2);

Yes. The rule engine is designed for computing a monotonic closure, not 
as a general purpose business rules engine, all non-monotonic operations 
like noValue are evil hacky additions for special uses. So if you need 
your rules to layer in a guaranteed order you have to cascade the InfModels.

Dave