private void checkIfNoNotPattern() { if (quantifier.getConsumingStrategy() == ConsumingStrategy.NOT_FOLLOW || quantifier.getConsumingStrategy() == ConsumingStrategy.NOT_NEXT) { throw new MalformedPatternException("Option not applicable to NOT pattern"); } }
public static Quantifier one(final ConsumingStrategy consumingStrategy) { return new Quantifier(consumingStrategy, QuantifierProperty.SINGLE); }
public void combinations() { checkPattern(!hasProperty(QuantifierProperty.SINGLE), "Combinations not applicable to " + this + "!"); checkPattern(innerConsumingStrategy != ConsumingStrategy.STRICT, "You can apply either combinations or consecutive, not both!"); checkPattern(innerConsumingStrategy != ConsumingStrategy.SKIP_TILL_ANY, "Combinations already applied!"); innerConsumingStrategy = ConsumingStrategy.SKIP_TILL_ANY; }
/** * Specifies that the pattern can occur between from and to times. * * @param from number of times matching event must appear at least * @param to number of times matching event must appear at most * @return The same pattern with the number of times range applied * * @throws MalformedPatternException if the quantifier is not applicable to this pattern. */ public Pattern<T, F> times(int from, int to) { checkIfNoNotPattern(); checkIfQuantifierApplied(); this.quantifier = Quantifier.times(quantifier.getConsumingStrategy()); if (from == 0) { this.quantifier.optional(); from = 1; } this.times = Times.of(from, to); return this; }
/** * Specifies that this pattern can occur the specified times at least. * This means at least the specified times and at most infinite number of events can * be matched to this pattern. * * @return The same pattern with a {@link Quantifier#looping(ConsumingStrategy)} quantifier applied. * @throws MalformedPatternException if the quantifier is not applicable to this pattern. */ public Pattern<T, F> timesOrMore(int times) { checkIfNoNotPattern(); checkIfQuantifierApplied(); this.quantifier = Quantifier.looping(quantifier.getConsumingStrategy()); this.times = Times.of(times); return this; }
private void checkIfQuantifierApplied() { if (!quantifier.hasProperty(Quantifier.QuantifierProperty.SINGLE)) { throw new MalformedPatternException("Already applied quantifier to this Pattern. " + "Current quantifier is: " + quantifier); } }
Quantifier.ConsumingStrategy consumingStrategy = pattern.getQuantifier().getConsumingStrategy(); if (headOfGroup(pattern)) { consumingStrategy = currentGroupPattern.getQuantifier().getConsumingStrategy(); } else { consumingStrategy = currentGroupPattern.getQuantifier().getInnerConsumingStrategy();
/** * Specifies exact number of times that this pattern should be matched. * * @param times number of times matching event must appear * @return The same pattern with number of times applied * * @throws MalformedPatternException if the quantifier is not applicable to this pattern. */ public Pattern<T, F> times(int times) { checkIfNoNotPattern(); checkIfQuantifierApplied(); Preconditions.checkArgument(times > 0, "You should give a positive number greater than 0."); this.quantifier = Quantifier.times(quantifier.getConsumingStrategy()); this.times = Times.of(times); return this; }
/** * Retrieves list of conditions resulting in Stop state and names of the corresponding NOT patterns. * * <p>A current not condition can be produced in two cases: * <ol> * <li>the previous pattern is a {@link Quantifier.ConsumingStrategy#NOT_FOLLOW}</li> * <li>exists a backward path of {@link Quantifier.QuantifierProperty#OPTIONAL} patterns to * {@link Quantifier.ConsumingStrategy#NOT_FOLLOW}</li> * </ol> * * <p><b>WARNING:</b> for more info on the second case see: {@link NFAFactoryCompiler#copyWithoutTransitiveNots(State)} * * @return list of not conditions with corresponding names */ private List<Tuple2<IterativeCondition<T>, String>> getCurrentNotCondition() { List<Tuple2<IterativeCondition<T>, String>> notConditions = new ArrayList<>(); Pattern<T, ? extends T> previousPattern = currentPattern; while (previousPattern.getPrevious() != null && ( previousPattern.getPrevious().getQuantifier().hasProperty(Quantifier.QuantifierProperty.OPTIONAL) || previousPattern.getPrevious().getQuantifier().getConsumingStrategy() == Quantifier.ConsumingStrategy.NOT_FOLLOW)) { previousPattern = previousPattern.getPrevious(); if (previousPattern.getQuantifier().getConsumingStrategy() == Quantifier.ConsumingStrategy.NOT_FOLLOW) { final IterativeCondition<T> notCondition = getTakeCondition(previousPattern); notConditions.add(Tuple2.of(notCondition, previousPattern.getName())); } } return notConditions; }
/** * Specifies that this pattern can occur {@code one or more} times. * This means at least one and at most infinite number of events can * be matched to this pattern. * * <p>If this quantifier is enabled for a * pattern {@code A.oneOrMore().followedBy(B)} and a sequence of events * {@code A1 A2 B} appears, this will generate patterns: * {@code A1 B} and {@code A1 A2 B}. See also {@link #allowCombinations()}. * * @return The same pattern with a {@link Quantifier#ONE_OR_MORE(ConsumingStrategy)} quantifier applied. * @throws MalformedPatternException if the quantifier is not applicable to this pattern. */ public Pattern<T, F> oneOrMore() { checkIfNoNotPattern(); checkIfQuantifierApplied(); this.quantifier = Quantifier.ONE_OR_MORE(quantifier.getConsumingStrategy()); return this; }
/** * Specifies exact number of times that this pattern should be matched. * * @param times number of times matching event must appear * @return The same pattern with number of times applied * * @throws MalformedPatternException if the quantifier is not applicable to this pattern. */ public Pattern<T, F> times(int times) { checkIfNoNotPattern(); checkIfQuantifierApplied(); Preconditions.checkArgument(times > 0, "You should give a positive number greater than 0."); this.quantifier = Quantifier.TIMES(quantifier.getConsumingStrategy()); this.times = times; return this; }
/** * Specifies that this pattern is optional for a final match of the pattern * sequence to happen. * * @return The same pattern as optional. * @throws MalformedPatternException if the quantifier is not applicable to this pattern. */ public Pattern<T, F> optional() { checkIfPreviousPatternGreedy(); quantifier.optional(); return this; }
/** * Applicable only to {@link Quantifier#looping(ConsumingStrategy)} and * {@link Quantifier#times(ConsumingStrategy)} patterns, this option allows more flexibility to the matching events. * * <p>If {@code allowCombinations()} is not applied for a * pattern {@code A.oneOrMore().followedBy(B)} and a sequence of events * {@code A1 A2 B} appears, this will generate patterns: * {@code A1 B} and {@code A1 A2 B}. If this method is applied, we * will have {@code A1 B}, {@code A2 B} and {@code A1 A2 B}. * * @return The same pattern with the updated quantifier. * * @throws MalformedPatternException if the quantifier is not applicable to this pattern. */ public Pattern<T, F> allowCombinations() { quantifier.combinations(); return this; }
Quantifier.ConsumingStrategy consumingStrategy = pattern.getQuantifier().getInnerConsumingStrategy(); if (headOfGroup(pattern)) { consumingStrategy = currentGroupPattern.getQuantifier().getInnerConsumingStrategy();
quantifier.consecutive(); return this;
/** * Specifies that this pattern is greedy. * This means as many events as possible will be matched to this pattern. * * @return The same pattern with {@link Quantifier#greedy} set to true. * @throws MalformedPatternException if the quantifier is not applicable to this pattern. */ public Pattern<T, F> greedy() { checkIfNoNotPattern(); checkIfNoGroupPattern(); this.quantifier.greedy(); return this; }
/** * Specifies that the pattern can occur between from and to times. * * @param from number of times matching event must appear at least * @param to number of times matching event must appear at most * @return The same pattern with the number of times range applied * * @throws MalformedPatternException if the quantifier is not applicable to this pattern. */ public Pattern<T, F> times(int from, int to) { checkIfNoNotPattern(); checkIfQuantifierApplied(); this.quantifier = Quantifier.times(quantifier.getConsumingStrategy()); if (from == 0) { this.quantifier.optional(); from = 1; } this.times = Times.of(from, to); return this; }
/** * Specifies that this pattern can occur {@code one or more} times. * This means at least one and at most infinite number of events can * be matched to this pattern. * * <p>If this quantifier is enabled for a * pattern {@code A.oneOrMore().followedBy(B)} and a sequence of events * {@code A1 A2 B} appears, this will generate patterns: * {@code A1 B} and {@code A1 A2 B}. See also {@link #allowCombinations()}. * * @return The same pattern with a {@link Quantifier#looping(ConsumingStrategy)} quantifier applied. * @throws MalformedPatternException if the quantifier is not applicable to this pattern. */ public Pattern<T, F> oneOrMore() { checkIfNoNotPattern(); checkIfQuantifierApplied(); this.quantifier = Quantifier.looping(quantifier.getConsumingStrategy()); this.times = Times.of(1); return this; }
/** * Appends a new pattern to the existing one. The new pattern enforces that there is no event matching this pattern * right after the preceding matched event. * * @param name Name of the new pattern * @return A new pattern which is appended to this one */ public Pattern<T, T> notNext(final String name) { if (quantifier.hasProperty(Quantifier.QuantifierProperty.OPTIONAL)) { throw new UnsupportedOperationException( "Specifying a pattern with an optional path to NOT condition is not supported yet. " + "You can simulate such pattern with two independent patterns, one with and the other without " + "the optional part."); } return new Pattern<>(name, this, ConsumingStrategy.NOT_NEXT, afterMatchSkipStrategy); }
Quantifier.ConsumingStrategy consumingStrategy = pattern.getQuantifier().getConsumingStrategy(); if (headOfGroup(pattern)) { consumingStrategy = currentGroupPattern.getQuantifier().getConsumingStrategy(); } else { consumingStrategy = currentGroupPattern.getQuantifier().getInnerConsumingStrategy();