[
https://issues.apache.org/jira/browse/FLINK-6198?page=com.atlassian.jira.plugin.system.issuetabpanels:comment-tabpanel&focusedCommentId=16032940#comment-16032940
]
ASF GitHub Bot commented on FLINK-6198:
---------------------------------------
Github user tzulitai commented on a diff in the pull request:
https://github.com/apache/flink/pull/4041#discussion_r119607288
--- Diff: docs/dev/libs/cep.md ---
@@ -246,63 +333,118 @@ pattern.where(event => ... /* some condition
*/).or(event => ... /* or condition
</div>
</div>
-Next, we can append further states to detect complex patterns.
-We can control the contiguity of two succeeding events to be accepted by
the pattern.
+##### Conditions on Contiguity
-Strict contiguity means that two matching events have to be directly the
one after the other.
-This means that no other events can occur in between.
-A strict contiguity pattern state can be created via the `next` method.
+FlinkCEP supports the following forms of contiguity between consecutive
events:
-<div class="codetabs" markdown="1">
-<div data-lang="java" markdown="1">
-{% highlight java %}
-Pattern<Event, ?> strictNext = start.next("middle");
-{% endhighlight %}
-</div>
+ 1. Strict Contiguity: which expects all matching events to appear
strictly the one after the other,
+ without any non-matching events in-between.
-<div data-lang="scala" markdown="1">
-{% highlight scala %}
-val strictNext: Pattern[Event, _] = start.next("middle")
-{% endhighlight %}
-</div>
-</div>
+ 2. Relaxed Contiguity: which simply ignores non-matching events appearing
in-between the matching ones.
+
+ 3. Non-Deterministic Relaxed Contiguity: which further relaxes contiguity
by also creating alternative
+ matches which ignore also matching events.
-Non-strict contiguity means that other events are allowed to occur
in-between two matching events.
-A non-strict contiguity pattern state can be created via the `followedBy`
or `followedByAny` method.
+To illustrate the above with an example, a pattern sequence `a+ b` (one or
more `a`s followed by a `b`) with
+input `a1, c, a2, b` will have the following results:
+
+ 1. Strict Contiguity: `a2 b` because there is `c` `a1` and `a2` so `a1`
is discarded.
+
+ 2. Relaxed Contiguity: `a1 b` and `a1 a2 b`, as `c` will get simply
ignored.
+
+ 3. Non-Deterministic Relaxed Contiguity: `a1 b`, `a2 b` and `a1 a2 b`.
+
+Contiguity conditions should be specified both within individual (looping)
states but also
+across states. For looping states (e.g. `oneOrMore()` and `times()`) the
default is *relaxed contiguity*. If you want
+strict contiguity, you have to explicitly specify it by using the
`consecutive()` call, and if you want
+*non-deterministic relaxed contiguity* you can use the
`allowCombinations()` call.
+
+### Combining States
+
+Now that we have seen how an individual state can look, it is time to see
how to combine them into a full pattern sequence.
+
+A pattern sequence has to start with an initial state, as shown below:
<div class="codetabs" markdown="1">
<div data-lang="java" markdown="1">
{% highlight java %}
-Pattern<Event, ?> nonStrictNext = start.followedBy("middle");
+Pattern<Event, ?> start = Pattern.<Event>begin("start");
{% endhighlight %}
</div>
<div data-lang="scala" markdown="1">
{% highlight scala %}
-val nonStrictNext : Pattern[Event, _] = start.followedBy("middle")
+val start : Pattern[Event, _] = Pattern.begin("start")
{% endhighlight %}
</div>
</div>
-For non-strict contiguity one can specify if only the first succeeding
matching event will be matched, or
-all. In the latter case multiple matches will be emitted for the same
beginning.
+Next, you can append more states to your pattern by specifying the desired
*contiguity conditions* between them.
+This can be done using:
+
+1. `next()`, for *strict*,
+2. `followedBy()`, for *relaxed*, and
+3. `followedByAny()`, for *non-deterministic relaxed* contiguity.
+
+or
+
+1. `notNext()`, if you do not want an event type to directly follow another
+2. `notFollowedBy()`, if you do not want an event type to be anywhere
between two other event types
+
+
+<span class="label label-danger">Attention</span> A pattern sequence
cannot end in `notFollowedBy()`.
+
+<span class="label label-danger">Attention</span> A `NOT` state cannot be
preceded by an optional one.
<div class="codetabs" markdown="1">
<div data-lang="java" markdown="1">
{% highlight java %}
-Pattern<Event, ?> nonStrictNext = start.followedByAny("middle");
+
+// strict contiguity
+Pattern<Event, ?> strict = start.next("middle").where(...);
+
+// relaxed contiguity
+Pattern<Event, ?> relaxed = start.followedBy("middle").where(...);
+
+// non-deterministic relaxed contiguity
+Pattern<Event, ?> nonDetermin = start.followedByAny("middle").where(...);
+
+// NOT pattern with strict contiguity
+Pattern<Event, ?> strictNot = start.notNext("not").where(...);
+
+// NOT pattern with relaxed contiguity
+Pattern<Event, ?> relaxedNot = start.notFollowedBy("not").where(...);
+
{% endhighlight %}
</div>
<div data-lang="scala" markdown="1">
{% highlight scala %}
-val nonStrictNext : Pattern[Event, _] = start.followedByAny("middle")
+
+// strict contiguity
+val strict: Pattern[Event, _] = start.next("middle").where(...)
+
+// relaxed contiguity
+val relaxed: Pattern[Event, _] = start.followedBy("middle").where(...)
+
+// non-deterministic relaxed contiguity
+val nonDetermin: Pattern[Event, _] =
start.followedByAny("middle").where(...)
+
+// NOT pattern with strict contiguity
+val strictNot: Pattern[Event, _] = start.notNext("not").where(...)
+
+// NOT pattern with relaxed contiguity
+val relaxedNot: Pattern[Event, _] = start.notFollowedBy("not").where(...)
+
{% endhighlight %}
</div>
-
</div>
-It is also possible to define a temporal constraint for the pattern to be
valid.
-For example, one can define that a pattern should occur within 10 seconds
via the `within` method.
+
+Bear in mind that relaxed contiguity means that only the first succeeding
matching event will be matched, while
+non-deterministic relaxed contiguity, multiple matches will be emitted for
the same beginning.
+
+Finally, it is also possible to define a temporal constraint for the
pattern to be valid.
+For example, you can define that a pattern should occur within 10 seconds
via the `pattern.within()` method.
Temporal patterns are supported for both [processing and event
time]({{site.baseurl}}/dev/event_time.html).
<div class="codetabs" markdown="1">
--- End diff --
I wonder if it makes sense to break up this table into 2 parts, one placed
under the "Individual States" section, and "Combining States" section, to make
it clearer which API calls are for describing the construction of an individual
state and which ones are for combining different states.
> Update the documentation of the CEP library to include all the new features.
> ----------------------------------------------------------------------------
>
> Key: FLINK-6198
> URL: https://issues.apache.org/jira/browse/FLINK-6198
> Project: Flink
> Issue Type: Sub-task
> Components: CEP
> Affects Versions: 1.3.0
> Reporter: Kostas Kloudas
> Assignee: Kostas Kloudas
> Priority: Critical
> Fix For: 1.3.0
>
>
> New features to include:
> * Iterative Functions
> * Quantifiers
> * Time handling
> * Migration from FilterFunction to IterativeCondition
--
This message was sent by Atlassian JIRA
(v6.3.15#6346)