Accumulate/Collect 基于时间运算符

Accumulate/Collect based on temporal operator

我正在尝试编写一个基于时间运算符收集/累积值的规则。

rule "Zone6 Overlap"
when
    $i1 : Instance ($e1 : event == " Vel : 20.99-23.98 km/h : " && $name1 : name) from entry-point "Stream"
    $i2 : Instance ($e2 : event && $name2 : name && $e2 == $e1 && $name2 != $name1 
    && this overlaps $i1) from entry-point "Stream"
then 
    System.out.println("** Overlap Event: Velocity Zone 6 ** \nPlayer1: " + $i1.getName() + "\nPlayer2: " 
    + $i2.getName() + "\nEvent: " + $i1.getEvent() + "\n" + "Start Time (P1): " 
    + $i1.getStart() + " - End Time: " + $i1.getEnd() + "\nStart Time (P2): " 
    + $i2.getStart() + " - End Time: " + $i2.getEnd() + "\n");
end

这是我的原始规则,它设法让两个持续时间重叠。

我想创建的规则的想法是查看足球比赛中球员的持续时间是否有任何集体重叠。我想看看场上最多 9 名球员中是否有任何球员以事件变量中指定为字符串的速度范围行进,这些速度全部同时重叠。

我已经尝试了一些关于累积和收集的事情,但是在这些事件发生时如何收集这些事件以及如何将它们 return 放在规则的右侧以便它们可以打印到标准输出方面很费力.

请帮忙。

谢谢。

应该可以创建一个规则来满足您的要求,但我认为您需要了解 Drools 中 overlaps 关键字的确切定义:

The overlaps evaluator correlates two events and matches when the current event starts before the correlated event starts and finishes after the correlated event starts, but before the correlated event finishes. In other words, both events have an overlapping period.

这意味着它不会匹配任何任意重叠,但前提是一个事件在另一个事件开始之前开始并且在该事件结束之前结束。假设我们有以下 3 个事件:

A [11:19:00-11:19:30]
B [11:19:15-11:19:45]
C [11:19:20-11:19:40]

在这种情况下,A 在 B 和 C 之前开始,也在两者之前结束。这意味着 A 与 B 和 C 重叠。但是,B 不与 C 重叠,因为它在 C 之前开始,但在 C 之后结束。有关每个可用运算符的完整定义,请参阅 Drools fusion documentation.

如果符合您的用例,则以下规则将收集与给定事件重叠的所有事件:

rule "Overlap"
when
    $i1 : Instance ($e1 : event == "some event" ) 
    $instances : List( size > 0 ) from collect ( Instance ( event == $e1, this != $i1, 
        this overlappedby $i1 ) )
then
    System.out.println("** Overlap Event for: " + $i1.getName());
    for (int i = 0; i < $instances.size(); i++) {
        System.out.println("Overlaps: " +  ((Instance)$instances.get(i)).getName());
    }
end

如您所见,它使用了 overlappedby 关键字,这是 overlaps.

的倒数