Search in sources :

Example 1 with NormalizedPredicate

use of com.pingcap.tikv.expression.ComparisonBinaryExpression.NormalizedPredicate in project tispark by pingcap.

the class ProtoConverter method visit.

@Override
protected Expr visit(ComparisonBinaryExpression node, Object context) {
    NormalizedPredicate predicate = node.normalize();
    if (predicate.getValue().isOverflowed()) {
        throw new UnsupportedOperationException("overflowed ComparisonBinaryExpression cannot be pushed down");
    }
    Expression child = node.getLeft();
    String typeSignature = getTypeSignature(child);
    ScalarFuncSig protoSig;
    switch(node.getComparisonType()) {
        case EQUAL:
            protoSig = ScalarFuncSig.valueOf("EQ" + typeSignature);
            break;
        case GREATER_EQUAL:
            protoSig = ScalarFuncSig.valueOf("GE" + typeSignature);
            break;
        case GREATER_THAN:
            protoSig = ScalarFuncSig.valueOf("GT" + typeSignature);
            break;
        case LESS_EQUAL:
            protoSig = ScalarFuncSig.valueOf("LE" + typeSignature);
            break;
        case LESS_THAN:
            protoSig = ScalarFuncSig.valueOf("LT" + typeSignature);
            break;
        case NOT_EQUAL:
            protoSig = ScalarFuncSig.valueOf("NE" + typeSignature);
            break;
        default:
            throw new TiExpressionException(String.format("Unknown comparison type %s", node.getComparisonType()));
    }
    Expr.Builder builder = scalarToPartialProto(node, context);
    builder.setSig(protoSig);
    builder.setFieldType(toPBFieldType(getType(node)));
    return builder.build();
}
Also used : Expr(com.pingcap.tidb.tipb.Expr) FuncCallExpr(com.pingcap.tikv.expression.FuncCallExpr) Expression(com.pingcap.tikv.expression.Expression) ArithmeticBinaryExpression(com.pingcap.tikv.expression.ArithmeticBinaryExpression) StringRegExpression(com.pingcap.tikv.expression.StringRegExpression) ComparisonBinaryExpression(com.pingcap.tikv.expression.ComparisonBinaryExpression) LogicalBinaryExpression(com.pingcap.tikv.expression.LogicalBinaryExpression) NormalizedPredicate(com.pingcap.tikv.expression.ComparisonBinaryExpression.NormalizedPredicate) TiExpressionException(com.pingcap.tikv.exception.TiExpressionException) ScalarFuncSig(com.pingcap.tidb.tipb.ScalarFuncSig)

Example 2 with NormalizedPredicate

use of com.pingcap.tikv.expression.ComparisonBinaryExpression.NormalizedPredicate in project tispark by pingcap.

the class RangeColumnPartitionPruner method visit.

@Override
protected Set<Integer> visit(ComparisonBinaryExpression node, LogicalBinaryExpression parent) {
    NormalizedPredicate predicate = node.normalize();
    if (predicate == null) {
        throw new UnsupportedOperationException(String.format("ComparisonBinaryExpression %s cannot be normalized", node.toString()));
    }
    String colRefName = predicate.getColumnRef().getName();
    List<Expression> partExprs = partExprsPerColumnRef.get(colRefName);
    Set<Integer> partDefs = new HashSet<>();
    if (partExprs == null) {
        switch(parent.getCompType()) {
            case OR:
                return partDefs;
            case AND:
                for (int i = 0; i < partsSize; i++) {
                    partDefs.add(i);
                }
                return partDefs;
        }
    }
    Objects.requireNonNull(partExprs, "partition expression cannot be null");
    for (int i = 0; i < partsSize; i++) {
        PrunedPartitionBuilder rangeBuilder = new PrunedPartitionBuilder(ImmutableSet.of(predicate.getColumnRef()));
        RangeSet<TypedKey> partExprRange = rangeBuilder.buildRange(partExprs.get(i));
        RangeSet<TypedKey> filterRange = rangeBuilder.buildRange(node);
        RangeSet<TypedKey> copy = TreeRangeSet.create(partExprRange);
        copy.removeAll(filterRange.complement());
        // part expr and filter is connected
        if (!copy.isEmpty()) {
            partDefs.add(i);
        }
    }
    return partDefs;
}
Also used : TypedKey(com.pingcap.tikv.key.TypedKey) NormalizedPredicate(com.pingcap.tikv.expression.ComparisonBinaryExpression.NormalizedPredicate) PrunedPartitionBuilder(com.pingcap.tikv.expression.visitor.PrunedPartitionBuilder) HashSet(java.util.HashSet)

Example 3 with NormalizedPredicate

use of com.pingcap.tikv.expression.ComparisonBinaryExpression.NormalizedPredicate in project tispark by pingcap.

the class RangeSetBuilder method visitComparisonBinaryExpr.

/**
 * visits {@code ComparisonBinaryExpression} expression and constructs a range set.
 *
 * @param node represents a {@code ComparisonBinaryExpression}.
 * @param context represents a context during visiting process. It is not being used in this
 *     method.
 * @param literal represents a comparable value.
 * @param loose If prefix length is specified, then filter is loose, so is the range.
 * @return a range set.
 */
RangeSet<C> visitComparisonBinaryExpr(ComparisonBinaryExpression node, Void context, C literal, boolean loose) {
    NormalizedPredicate predicate = node.normalize();
    RangeSet<C> ranges = TreeRangeSet.create();
    if (loose) {
        switch(predicate.getType()) {
            case GREATER_THAN:
            case GREATER_EQUAL:
                ranges.add(Range.atLeast(literal));
                break;
            case LESS_THAN:
            case LESS_EQUAL:
                ranges.add(Range.atMost(literal));
                break;
            case EQUAL:
                ranges.add(Range.singleton(literal));
                break;
            case NOT_EQUAL:
                // Should return full range because prefix index predicate for NOT_EQUAL
                // will be split into an NOT_EQUAL filter and a full range scan
                ranges.add(Range.all());
                break;
            default:
                throwOnError(node);
        }
    } else {
        switch(predicate.getType()) {
            case GREATER_THAN:
                ranges.add(Range.greaterThan(literal));
                break;
            case GREATER_EQUAL:
                ranges.add(Range.atLeast(literal));
                break;
            case LESS_THAN:
                ranges.add(Range.lessThan(literal));
                break;
            case LESS_EQUAL:
                ranges.add(Range.atMost(literal));
                break;
            case EQUAL:
                ranges.add(Range.singleton(literal));
                break;
            case NOT_EQUAL:
                ranges.add(Range.lessThan(literal));
                ranges.add(Range.greaterThan(literal));
                break;
            default:
                throwOnError(node);
        }
    }
    return ranges;
}
Also used : NormalizedPredicate(com.pingcap.tikv.expression.ComparisonBinaryExpression.NormalizedPredicate)

Example 4 with NormalizedPredicate

use of com.pingcap.tikv.expression.ComparisonBinaryExpression.NormalizedPredicate in project tispark by pingcap.

the class ComparisonBinaryExpressionTest method verifyNormalize.

private void verifyNormalize(ComparisonBinaryExpression cond, String colName, Object value, DataType dataType, Operator operator) {
    NormalizedPredicate normCond = cond.normalize();
    assertEquals(colName, normCond.getColumnRef().getName());
    assertEquals(value, normCond.getValue().getValue());
    assertEquals(TypedKey.toTypedKey(value, dataType), normCond.getTypedLiteral());
    assertEquals(operator, normCond.getType());
}
Also used : NormalizedPredicate(com.pingcap.tikv.expression.ComparisonBinaryExpression.NormalizedPredicate)

Example 5 with NormalizedPredicate

use of com.pingcap.tikv.expression.ComparisonBinaryExpression.NormalizedPredicate in project tispark by pingcap.

the class IndexRangeSetBuilder method visit.

@Override
protected RangeSet<TypedKey> visit(ComparisonBinaryExpression node, Void context) {
    NormalizedPredicate predicate = node.normalize();
    if (predicate == null) {
        throwOnError(node);
    }
    // In order to match a prefix index, we have to cut the literal by prefix length.
    // e.g., for table t:
    // CREATE TABLE `t` {
    // `b` VARCHAR(10) DEFAULT NULL,
    // KEY `prefix_index` (`b`(2))
    // }
    // 
    // b(2) > "bbc" -> ["bb", +∞)
    // b(2) >= "bbc" -> ["bb", +∞)
    // b(2) < "bbc" -> (-∞, "bb"]
    // b(2) <= "bbc" -> (-∞, "bb"]
    // b(2) = "bbc" -> ["bb", "bb"]
    // b(2) > "b" -> ["b", +∞)
    // b(2) >= "b" -> ["b", +∞)
    // b(2) < "b" -> (-∞, "b"]
    // b(2) <= "b" -> (-∞, "b"]
    // 
    // For varchar, `b`(2) will take first two characters(bytes) as prefix index.
    // TODO: Note that TiDB only supports UTF-8, we need to check if prefix index behave differently
    // under other encoding methods
    int prefixLen = lengths.getOrDefault(predicate.getColumnRef(), DataType.UNSPECIFIED_LEN);
    TypedKey literal = predicate.getTypedLiteral(prefixLen);
    boolean loose = !DataType.isLengthUnSpecified(prefixLen);
    // With prefix length specified, the filter is loosen and so should the ranges
    return visitComparisonBinaryExpr(node, context, literal, loose);
}
Also used : TypedKey(com.pingcap.tikv.key.TypedKey) NormalizedPredicate(com.pingcap.tikv.expression.ComparisonBinaryExpression.NormalizedPredicate)

Aggregations

NormalizedPredicate (com.pingcap.tikv.expression.ComparisonBinaryExpression.NormalizedPredicate)7 TypedKey (com.pingcap.tikv.key.TypedKey)3 ComparisonBinaryExpression (com.pingcap.tikv.expression.ComparisonBinaryExpression)2 Expression (com.pingcap.tikv.expression.Expression)2 FuncCallExpr (com.pingcap.tikv.expression.FuncCallExpr)2 LogicalBinaryExpression (com.pingcap.tikv.expression.LogicalBinaryExpression)2 Expr (com.pingcap.tidb.tipb.Expr)1 ScalarFuncSig (com.pingcap.tidb.tipb.ScalarFuncSig)1 TiExpressionException (com.pingcap.tikv.exception.TiExpressionException)1 ArithmeticBinaryExpression (com.pingcap.tikv.expression.ArithmeticBinaryExpression)1 Constant (com.pingcap.tikv.expression.Constant)1 StringRegExpression (com.pingcap.tikv.expression.StringRegExpression)1 PrunedPartitionBuilder (com.pingcap.tikv.expression.visitor.PrunedPartitionBuilder)1 HashSet (java.util.HashSet)1