[rules-users] Easy mistake... - drools operator precedence

Willem van Asperen willem at van.asperen.org
Mon Feb 18 10:34:45 EST 2013


On 02/18/2013 02:35 PM, Geoffrey De Smet wrote:
>
> Op 18-02-13 14:00, Willem van Asperen schreef:
>> On 02/18/2013 11:11 AM, Willem van Asperen wrote:
>>> Hi All,
>>>
>>> Just wanted to share with you an easy mistake. This is done running
>>> Drools 5.5.0.Final.
>>>
>>> Imagine a fact
>>>
>>> |Cheese (||
>>> ||    creationTick : double||
>>> ||    preservationTicks : double||
>>> ||)|
>>>
>>> Then the following does not do what you expect:
>>>
>>> |rule "dump old cheese"||
>>> ||    when||
>>> ||        $c : Cheese( $sbd : creationTick + preservationTicks )||
>>> ||        CurrentTime( tick >= $sbd )||
>>> ||    then||
>>> ||        System.out.println("||we have to dump "+$c);||
>>> ||end|
>>>
>>> You would expect that $c is dumped when current time has passed
>>> creationTick + preservationTicks. But no. The variable $sbd is bound
>>> to creationTick /before/ the preservationTicks are added!! I must
>>> say that I do not quite understand how ($sbd : creationTick) +
>>> preservationTicks resolves to "true" to make the premise succeed...
>>> Maybe because it is != 0?
>>>
>>> I found that it should be:
>>>
>>> |rule "dump old cheese"||
>>> ||    when||
>>> ||        $c : Cheese( $sbd : (creationTick + preservationTicks) )||
>>> ||        CurrentTime( tick >= $sbd )||
>>> ||    then||
>>> ||        System.out.println("we have to dump "+$c);||
>>> ||end|
>>>
>>> This makes sense. Now $sbd is bound to the result of the addition.
>>> But it is an easy trap!!
>>>
>>> Regards,
>>> Willem
>> Hi All,
>>
>> Coming back to this... What will be evaluated in the following snippet:
>>
>> rule "dump old cheese"
>>     when
>>         CurrentTime( $tick : tick )
>>         $c : Cheese( $tick >= creationTick + preservationTicks )
>>     then
>>         System.out.println("we need to dump "+$c);
>> end
>>
>> I assume this evaluates if $tick is larger or equal to (creationTick
>> + preservationTicks), right?
> I think so too.
> It looks like the : operator has a higher precedence then + (and
> therefor >= too), which is a bit surprising indeed.
> Personally, I never mix the : operator with other operators, to avoid
> having to worry about the precendence.
So you would write:

|rule "dump old cheese"||
||    when||
||        $c : Cheese( $ct : creationTick, $p : preservationTicks )||
||        CurrentTime( tick >= $ct + $p )||
||    then||
||        System.out.println("we have to dump "+$c);||
||end
|       
Assuming + takes precedence over >=.

The reason I am binding the sum to creationTick and preservationTicks to
a variable is that I am using that variable in multiple places and do
not want the engine to have to calculate the sum for every occurrence.
Also: it makes the rule more readable in my view.
>> Otherwise it would say
>>
>> step 1:    $tick > creationTick + preservationTicks
>> step 2:    true + preservationTicks
>>
>> which would fail, obviously because you cannot add a double to a boolean.
>>
>> Regards,
>> Willem
>>
>>
>> _______________________________________________
>> rules-users mailing list
>> rules-users at lists.jboss.org
>> https://lists.jboss.org/mailman/listinfo/rules-users
>

-------------- next part --------------
An HTML attachment was scrubbed...
URL: http://lists.jboss.org/pipermail/rules-users/attachments/20130218/52c0ab4b/attachment.html 


More information about the rules-users mailing list