private void removeTimeFilters(List<Expression> expressions, Expression expression) { if (expression.op() == Operation.AND) { And and = (And) expression; removeTimeFilters(expressions, and.left()); removeTimeFilters(expressions, and.right()); return; } else if (expression instanceof UnboundPredicate) { UnboundPredicate pred = (UnboundPredicate) expression; NamedReference ref = (NamedReference) pred.ref(); Literal<?> lit = pred.literal(); if (TIMESTAMP_NAMES.contains(ref.name())) { Literal<Long> tsLiteral = lit.to(Types.TimestampType.withoutZone()); long millis = toMillis(tsLiteral.value()); addTimestampFilter(Expressions.predicate(pred.op(), "timestamp_ms", millis)); return; } } expressions.add(expression); }
public static Expression and(Expression left, Expression right) { Preconditions.checkNotNull(left, "Left expression cannot be null."); Preconditions.checkNotNull(right, "Right expression cannot be null."); if (left == alwaysFalse() || right == alwaysFalse()) { return alwaysFalse(); } else if (left == alwaysTrue()) { return right; } else if (right == alwaysTrue()) { return left; } return new And(left, right); }
private static boolean equals(Expression left, Expression right) { if (left.op() != right.op()) { return false; } if (left instanceof Predicate) { if (!(left.getClass().isInstance(right))) { return false; } return equals((Predicate) left, (Predicate) right); } switch (left.op()) { case FALSE: case TRUE: return true; case NOT: return equals(((Not) left).child(), ((Not) right).child()); case AND: return ( equals(((And) left).left(), ((And) right).left()) && equals(((And) left).right(), ((And) right).right()) ); case OR: return ( equals(((Or) left).left(), ((Or) right).left()) && equals(((Or) left).right(), ((Or) right).right()) ); default: return false; } }
@Test public void testAnd() { Expression expr = and(equal("x", 7), lessThan("y", 100)); Expression boundExpr = Binder.bind(STRUCT, expr); TestHelpers.assertAllReferencesBound("And", boundExpr); // make sure the result is an And And and = TestHelpers.assertAndUnwrap(boundExpr, And.class); // make sure the refs are for the right fields BoundPredicate<?> left = TestHelpers.assertAndUnwrap(and.left()); Assert.assertEquals("Should bind x correctly", 0, left.ref().fieldId()); BoundPredicate<?> right = TestHelpers.assertAndUnwrap(and.right()); Assert.assertEquals("Should bind y correctly", 1, right.ref().fieldId()); }