Search in sources :

Example 1 with DomainTranslator

use of com.facebook.presto.spi.relation.DomainTranslator in project presto by prestodb.

the class PickTableLayout method pushPredicateIntoTableScan.

/**
 * For RowExpression {@param predicate}
 */
private static PlanNode pushPredicateIntoTableScan(TableScanNode node, RowExpression predicate, boolean pruneWithPredicateExpression, Session session, PlanNodeIdAllocator idAllocator, Metadata metadata, DomainTranslator domainTranslator) {
    // don't include non-deterministic predicates
    LogicalRowExpressions logicalRowExpressions = new LogicalRowExpressions(new RowExpressionDeterminismEvaluator(metadata.getFunctionAndTypeManager()), new FunctionResolution(metadata.getFunctionAndTypeManager()), metadata.getFunctionAndTypeManager());
    RowExpression deterministicPredicate = logicalRowExpressions.filterDeterministicConjuncts(predicate);
    DomainTranslator.ExtractionResult<VariableReferenceExpression> decomposedPredicate = domainTranslator.fromPredicate(session.toConnectorSession(), deterministicPredicate, BASIC_COLUMN_EXTRACTOR);
    TupleDomain<ColumnHandle> newDomain = decomposedPredicate.getTupleDomain().transform(variableName -> node.getAssignments().get(variableName)).intersect(node.getEnforcedConstraint());
    Map<ColumnHandle, VariableReferenceExpression> assignments = ImmutableBiMap.copyOf(node.getAssignments()).inverse();
    Constraint<ColumnHandle> constraint;
    if (pruneWithPredicateExpression) {
        LayoutConstraintEvaluatorForRowExpression evaluator = new LayoutConstraintEvaluatorForRowExpression(metadata, session, node.getAssignments(), logicalRowExpressions.combineConjuncts(deterministicPredicate, // which would be expensive to evaluate in the call to isCandidate below.
        domainTranslator.toPredicate(newDomain.simplify().transform(column -> assignments.getOrDefault(column, null)))));
        constraint = new Constraint<>(newDomain, evaluator::isCandidate);
    } else {
        // Currently, invoking the expression interpreter is very expensive.
        // TODO invoke the interpreter unconditionally when the interpreter becomes cheap enough.
        constraint = new Constraint<>(newDomain);
    }
    if (constraint.getSummary().isNone()) {
        return new ValuesNode(node.getSourceLocation(), idAllocator.getNextId(), node.getOutputVariables(), ImmutableList.of());
    }
    // Layouts will be returned in order of the connector's preference
    TableLayoutResult layout = metadata.getLayout(session, node.getTable(), constraint, Optional.of(node.getOutputVariables().stream().map(variable -> node.getAssignments().get(variable)).collect(toImmutableSet())));
    if (layout.getLayout().getPredicate().isNone()) {
        return new ValuesNode(node.getSourceLocation(), idAllocator.getNextId(), node.getOutputVariables(), ImmutableList.of());
    }
    TableScanNode tableScan = new TableScanNode(node.getSourceLocation(), node.getId(), layout.getLayout().getNewTableHandle(), node.getOutputVariables(), node.getAssignments(), layout.getLayout().getPredicate(), computeEnforced(newDomain, layout.getUnenforcedConstraint()));
    // The order of the arguments to combineConjuncts matters:
    // * Unenforced constraints go first because they can only be simple column references,
    // which are not prone to logic errors such as out-of-bound access, div-by-zero, etc.
    // * Conjuncts in non-deterministic expressions and non-TupleDomain-expressible expressions should
    // retain their original (maybe intermixed) order from the input predicate. However, this is not implemented yet.
    // * Short of implementing the previous bullet point, the current order of non-deterministic expressions
    // and non-TupleDomain-expressible expressions should be retained. Changing the order can lead
    // to failures of previously successful queries.
    RowExpression resultingPredicate = logicalRowExpressions.combineConjuncts(domainTranslator.toPredicate(layout.getUnenforcedConstraint().transform(assignments::get)), logicalRowExpressions.filterNonDeterministicConjuncts(predicate), decomposedPredicate.getRemainingExpression());
    if (!TRUE_CONSTANT.equals(resultingPredicate)) {
        return new FilterNode(node.getSourceLocation(), idAllocator.getNextId(), tableScan, resultingPredicate);
    }
    return tableScan;
}
Also used : RowExpressionDomainTranslator(com.facebook.presto.sql.relational.RowExpressionDomainTranslator) VariableReferenceExpression(com.facebook.presto.spi.relation.VariableReferenceExpression) Pattern(com.facebook.presto.matching.Pattern) TryFunction(com.facebook.presto.operator.scalar.TryFunction) ValuesNode(com.facebook.presto.spi.plan.ValuesNode) Preconditions.checkArgument(com.google.common.base.Preconditions.checkArgument) Capture(com.facebook.presto.matching.Capture) Map(java.util.Map) RowExpressionInterpreter(com.facebook.presto.sql.planner.RowExpressionInterpreter) ImmutableSet(com.google.common.collect.ImmutableSet) NullableValue(com.facebook.presto.common.predicate.NullableValue) ImmutableMap(com.google.common.collect.ImmutableMap) TableLayoutResult.computeEnforced(com.facebook.presto.metadata.TableLayoutResult.computeEnforced) DomainTranslator(com.facebook.presto.spi.relation.DomainTranslator) Set(java.util.Set) TRUE_CONSTANT(com.facebook.presto.expressions.LogicalRowExpressions.TRUE_CONSTANT) Objects(java.util.Objects) Capture.newCapture(com.facebook.presto.matching.Capture.newCapture) Optional(java.util.Optional) TableLayoutResult(com.facebook.presto.metadata.TableLayoutResult) Captures(com.facebook.presto.matching.Captures) RowExpressionDeterminismEvaluator(com.facebook.presto.sql.relational.RowExpressionDeterminismEvaluator) ConstantExpression(com.facebook.presto.spi.relation.ConstantExpression) Function(java.util.function.Function) Patterns.filter(com.facebook.presto.sql.planner.plan.Patterns.filter) ImmutableBiMap(com.google.common.collect.ImmutableBiMap) FilterNode(com.facebook.presto.spi.plan.FilterNode) SystemSessionProperties.isNewOptimizerEnabled(com.facebook.presto.SystemSessionProperties.isNewOptimizerEnabled) ImmutableList(com.google.common.collect.ImmutableList) LogicalRowExpressions(com.facebook.presto.expressions.LogicalRowExpressions) BASIC_COLUMN_EXTRACTOR(com.facebook.presto.spi.relation.DomainTranslator.BASIC_COLUMN_EXTRACTOR) Objects.requireNonNull(java.util.Objects.requireNonNull) ImmutableSet.toImmutableSet(com.google.common.collect.ImmutableSet.toImmutableSet) TableHandle(com.facebook.presto.spi.TableHandle) FunctionResolution(com.facebook.presto.sql.relational.FunctionResolution) VariablesExtractor(com.facebook.presto.sql.planner.VariablesExtractor) RowExpression(com.facebook.presto.spi.relation.RowExpression) VariableResolver(com.facebook.presto.sql.planner.VariableResolver) PlanNodeIdAllocator(com.facebook.presto.spi.plan.PlanNodeIdAllocator) Session(com.facebook.presto.Session) Rule(com.facebook.presto.sql.planner.iterative.Rule) Constraint(com.facebook.presto.spi.Constraint) TupleDomain(com.facebook.presto.common.predicate.TupleDomain) PreconditionRules.checkRulesAreFiredBeforeAddExchangesRule(com.facebook.presto.sql.planner.iterative.rule.PreconditionRules.checkRulesAreFiredBeforeAddExchangesRule) OPTIMIZED(com.facebook.presto.spi.relation.ExpressionOptimizer.Level.OPTIMIZED) Patterns.source(com.facebook.presto.sql.planner.plan.Patterns.source) PlanNode(com.facebook.presto.spi.plan.PlanNode) ColumnHandle(com.facebook.presto.spi.ColumnHandle) TableScanNode(com.facebook.presto.spi.plan.TableScanNode) Sets.intersection(com.google.common.collect.Sets.intersection) Patterns.tableScan(com.facebook.presto.sql.planner.plan.Patterns.tableScan) Metadata(com.facebook.presto.metadata.Metadata) RowExpressionDeterminismEvaluator(com.facebook.presto.sql.relational.RowExpressionDeterminismEvaluator) ColumnHandle(com.facebook.presto.spi.ColumnHandle) ValuesNode(com.facebook.presto.spi.plan.ValuesNode) LogicalRowExpressions(com.facebook.presto.expressions.LogicalRowExpressions) FilterNode(com.facebook.presto.spi.plan.FilterNode) RowExpression(com.facebook.presto.spi.relation.RowExpression) TableLayoutResult(com.facebook.presto.metadata.TableLayoutResult) FunctionResolution(com.facebook.presto.sql.relational.FunctionResolution) TableScanNode(com.facebook.presto.spi.plan.TableScanNode) VariableReferenceExpression(com.facebook.presto.spi.relation.VariableReferenceExpression) RowExpressionDomainTranslator(com.facebook.presto.sql.relational.RowExpressionDomainTranslator) DomainTranslator(com.facebook.presto.spi.relation.DomainTranslator)

Aggregations

Session (com.facebook.presto.Session)1 SystemSessionProperties.isNewOptimizerEnabled (com.facebook.presto.SystemSessionProperties.isNewOptimizerEnabled)1 NullableValue (com.facebook.presto.common.predicate.NullableValue)1 TupleDomain (com.facebook.presto.common.predicate.TupleDomain)1 LogicalRowExpressions (com.facebook.presto.expressions.LogicalRowExpressions)1 TRUE_CONSTANT (com.facebook.presto.expressions.LogicalRowExpressions.TRUE_CONSTANT)1 Capture (com.facebook.presto.matching.Capture)1 Capture.newCapture (com.facebook.presto.matching.Capture.newCapture)1 Captures (com.facebook.presto.matching.Captures)1 Pattern (com.facebook.presto.matching.Pattern)1 Metadata (com.facebook.presto.metadata.Metadata)1 TableLayoutResult (com.facebook.presto.metadata.TableLayoutResult)1 TableLayoutResult.computeEnforced (com.facebook.presto.metadata.TableLayoutResult.computeEnforced)1 TryFunction (com.facebook.presto.operator.scalar.TryFunction)1 ColumnHandle (com.facebook.presto.spi.ColumnHandle)1 Constraint (com.facebook.presto.spi.Constraint)1 TableHandle (com.facebook.presto.spi.TableHandle)1 FilterNode (com.facebook.presto.spi.plan.FilterNode)1 PlanNode (com.facebook.presto.spi.plan.PlanNode)1 PlanNodeIdAllocator (com.facebook.presto.spi.plan.PlanNodeIdAllocator)1