Search in sources :

Example 1 with DrillLimitRel

use of org.apache.drill.exec.planner.logical.DrillLimitRel in project drill by axbaretto.

the class LimitPrule method onMatch.

@Override
public void onMatch(RelOptRuleCall call) {
    final DrillLimitRel limit = (DrillLimitRel) call.rel(0);
    final RelNode input = limit.getInput();
    final RelTraitSet traits = input.getTraitSet().plus(Prel.DRILL_PHYSICAL).plus(DrillDistributionTrait.SINGLETON);
    final RelNode convertedInput = convert(input, traits);
    LimitPrel newLimit = new LimitPrel(limit.getCluster(), limit.getTraitSet().plus(Prel.DRILL_PHYSICAL).plus(DrillDistributionTrait.SINGLETON), convertedInput, limit.getOffset(), limit.getFetch());
    call.transformTo(newLimit);
}
Also used : RelNode(org.apache.calcite.rel.RelNode) RelTraitSet(org.apache.calcite.plan.RelTraitSet) DrillLimitRel(org.apache.drill.exec.planner.logical.DrillLimitRel)

Example 2 with DrillLimitRel

use of org.apache.drill.exec.planner.logical.DrillLimitRel in project drill by apache.

the class JoinUtils method isScalarSubquery.

/**
 * Utility method to check if a subquery (represented by its root RelNode) is provably scalar. Currently
 * only aggregates with no group-by are considered scalar. In the future, this method should be generalized
 * to include more cases and reconciled with Calcite's notion of scalar.
 * @param root The root RelNode to be examined
 * @return True if the root rel or its descendant is scalar, False otherwise
 */
public static boolean isScalarSubquery(RelNode root) {
    DrillAggregateRel agg = null;
    RelNode currentrel = root;
    while (agg == null && currentrel != null) {
        if (currentrel instanceof DrillAggregateRel) {
            agg = (DrillAggregateRel) currentrel;
        } else if (currentrel instanceof RelSubset) {
            currentrel = ((RelSubset) currentrel).getBest();
        } else if (currentrel instanceof DrillLimitRel) {
            // TODO: Improve this check when DRILL-5691 is fixed.
            // The problem is that RelMdMaxRowCount currently cannot be used
            // due to CALCITE-1048.
            Integer fetchValue = ((RexLiteral) ((DrillLimitRel) currentrel).getFetch()).getValueAs(Integer.class);
            return fetchValue != null && fetchValue <= 1;
        } else if (currentrel.getInputs().size() == 1) {
            // If the rel is not an aggregate or RelSubset, but is a single-input rel (could be Project,
            // Filter, Sort etc.), check its input
            currentrel = currentrel.getInput(0);
        } else {
            break;
        }
    }
    if (agg != null) {
        if (agg.getGroupSet().isEmpty()) {
            return true;
        }
        // with empty call list and literal from project expression in group set.
        if (agg.getAggCallList().isEmpty() && agg.getGroupSet().cardinality() == 1) {
            ProjectExpressionsCollector expressionsCollector = new ProjectExpressionsCollector();
            agg.accept(expressionsCollector);
            List<RexNode> projectedExpressions = expressionsCollector.getProjectedExpressions();
            return projectedExpressions.size() == 1 && RexUtil.isLiteral(projectedExpressions.get(agg.getGroupSet().nth(0)), true);
        }
    }
    return false;
}
Also used : RexLiteral(org.apache.calcite.rex.RexLiteral) RelNode(org.apache.calcite.rel.RelNode) DrillAggregateRel(org.apache.drill.exec.planner.logical.DrillAggregateRel) RelSubset(org.apache.calcite.plan.volcano.RelSubset) DrillLimitRel(org.apache.drill.exec.planner.logical.DrillLimitRel) RexNode(org.apache.calcite.rex.RexNode)

Example 3 with DrillLimitRel

use of org.apache.drill.exec.planner.logical.DrillLimitRel in project drill by apache.

the class LimitPrule method onMatch.

@Override
public void onMatch(RelOptRuleCall call) {
    final DrillLimitRel limit = (DrillLimitRel) call.rel(0);
    final RelNode input = limit.getInput();
    final RelTraitSet traits = input.getTraitSet().plus(Prel.DRILL_PHYSICAL).plus(DrillDistributionTrait.SINGLETON);
    final RelNode convertedInput = convert(input, traits);
    LimitPrel newLimit = new LimitPrel(limit.getCluster(), limit.getTraitSet().plus(Prel.DRILL_PHYSICAL).plus(DrillDistributionTrait.SINGLETON), convertedInput, limit.getOffset(), limit.getFetch());
    call.transformTo(newLimit);
}
Also used : RelNode(org.apache.calcite.rel.RelNode) RelTraitSet(org.apache.calcite.plan.RelTraitSet) DrillLimitRel(org.apache.drill.exec.planner.logical.DrillLimitRel)

Example 4 with DrillLimitRel

use of org.apache.drill.exec.planner.logical.DrillLimitRel in project drill by apache.

the class FindLimit0Visitor method addLimitOnTopOfLeafNodes.

public static DrillRel addLimitOnTopOfLeafNodes(final DrillRel rel) {
    final Pointer<Boolean> isUnsupported = new Pointer<>(false);
    // to visit unsupported functions
    final RexShuttle unsupportedFunctionsVisitor = new RexShuttle() {

        @Override
        public RexNode visitCall(RexCall call) {
            final SqlOperator operator = call.getOperator();
            if (isUnsupportedScalarFunction(operator)) {
                isUnsupported.value = true;
                return call;
            }
            return super.visitCall(call);
        }
    };
    // to visit unsupported operators
    final RelShuttle unsupportedOperationsVisitor = new RelShuttleImpl() {

        @Override
        public RelNode visit(RelNode other) {
            if (other instanceof DrillUnionRelBase) {
                isUnsupported.value = true;
                return other;
            } else if (other instanceof DrillProjectRelBase) {
                if (!isUnsupported.value) {
                    other.accept(unsupportedFunctionsVisitor);
                }
                if (isUnsupported.value) {
                    return other;
                }
            }
            return super.visit(other);
        }
    };
    rel.accept(unsupportedOperationsVisitor);
    if (isUnsupported.value) {
        return rel;
    }
    // to add LIMIT (0) on top of leaf nodes
    final RelShuttle addLimitOnScanVisitor = new RelShuttleImpl() {

        private RelNode addLimitAsParent(RelNode node) {
            final RexBuilder builder = node.getCluster().getRexBuilder();
            final RexLiteral offset = builder.makeExactLiteral(BigDecimal.ZERO);
            final RexLiteral fetch = builder.makeExactLiteral(BigDecimal.ZERO);
            return new DrillLimitRel(node.getCluster(), node.getTraitSet(), node, offset, fetch);
        }

        @Override
        public RelNode visit(LogicalValues values) {
            return addLimitAsParent(values);
        }

        @Override
        public RelNode visit(TableScan scan) {
            return addLimitAsParent(scan);
        }

        @Override
        public RelNode visit(RelNode other) {
            if (other.getInputs().isEmpty()) {
                // leaf operator
                return addLimitAsParent(other);
            }
            return super.visit(other);
        }
    };
    return (DrillRel) rel.accept(addLimitOnScanVisitor);
}
Also used : RexLiteral(org.apache.calcite.rex.RexLiteral) TableScan(org.apache.calcite.rel.core.TableScan) RexShuttle(org.apache.calcite.rex.RexShuttle) DrillSqlOperator(org.apache.drill.exec.planner.sql.DrillSqlOperator) SqlOperator(org.apache.calcite.sql.SqlOperator) RelShuttle(org.apache.calcite.rel.RelShuttle) RelShuttleImpl(org.apache.calcite.rel.RelShuttleImpl) Pointer(org.apache.drill.exec.util.Pointer) DrillProjectRelBase(org.apache.drill.exec.planner.common.DrillProjectRelBase) DrillLimitRel(org.apache.drill.exec.planner.logical.DrillLimitRel) LogicalValues(org.apache.calcite.rel.logical.LogicalValues) RexCall(org.apache.calcite.rex.RexCall) RelNode(org.apache.calcite.rel.RelNode) DrillUnionRelBase(org.apache.drill.exec.planner.common.DrillUnionRelBase) RexBuilder(org.apache.calcite.rex.RexBuilder) DrillRel(org.apache.drill.exec.planner.logical.DrillRel)

Aggregations

RelNode (org.apache.calcite.rel.RelNode)4 DrillLimitRel (org.apache.drill.exec.planner.logical.DrillLimitRel)4 RelTraitSet (org.apache.calcite.plan.RelTraitSet)2 RexLiteral (org.apache.calcite.rex.RexLiteral)2 RelSubset (org.apache.calcite.plan.volcano.RelSubset)1 RelShuttle (org.apache.calcite.rel.RelShuttle)1 RelShuttleImpl (org.apache.calcite.rel.RelShuttleImpl)1 TableScan (org.apache.calcite.rel.core.TableScan)1 LogicalValues (org.apache.calcite.rel.logical.LogicalValues)1 RexBuilder (org.apache.calcite.rex.RexBuilder)1 RexCall (org.apache.calcite.rex.RexCall)1 RexNode (org.apache.calcite.rex.RexNode)1 RexShuttle (org.apache.calcite.rex.RexShuttle)1 SqlOperator (org.apache.calcite.sql.SqlOperator)1 DrillProjectRelBase (org.apache.drill.exec.planner.common.DrillProjectRelBase)1 DrillUnionRelBase (org.apache.drill.exec.planner.common.DrillUnionRelBase)1 DrillAggregateRel (org.apache.drill.exec.planner.logical.DrillAggregateRel)1 DrillRel (org.apache.drill.exec.planner.logical.DrillRel)1 DrillSqlOperator (org.apache.drill.exec.planner.sql.DrillSqlOperator)1 Pointer (org.apache.drill.exec.util.Pointer)1