@Override public void onMatch(RelOptRuleCall call) { final Filter fil = call.rel(0); final TableScan rel = call.rel(1); // Add identity RelBuilder relBuilder = call.builder(); relBuilder.push(rel); List<RexNode> identityFields = relBuilder.fields( ImmutableBitSet.range(0, rel.getRowType().getFieldCount()).asList()); RelNode newRel = relBuilder .project(identityFields, ImmutableList.<String>of(), true) .build(); call.transformTo(fil.copy(fil.getTraitSet(), ImmutableList.of(newRel))); }
final Sort first = call.rel(1); final Sort second = call.rel(0); first.getInput(), first.getCollation(), offset == 0 ? null : call.builder().literal(offset), call.builder().literal(fetch) ); call.transformTo(combined); call.getPlanner().setImportance(second, 0.0);
@Override public void onMatch(RelOptRuleCall call) { final Filter filter = call.rel(0); final RexBuilder rexBuilder = filter.getCluster().getRexBuilder(); final RelMetadataQuery metadataProvider = call.getMetadataQuery(); // 1. Recompose filter possibly by pulling out common elements from DNF // expressions RexNode newFilterCondition = RexUtil.pullFactors(rexBuilder, filter.getCondition()); // 2. Reduce filter with stats information RexReplacer replacer = new RexReplacer(filter, rexBuilder, metadataProvider); newFilterCondition = replacer.apply(newFilterCondition); // 3. Transform if we have created a new filter operator if (!filter.getCondition().toString().equals(newFilterCondition.toString())) { Filter newFilter = filter.copy(filter.getTraitSet(), filter.getInput(), newFilterCondition); call.transformTo(newFilter); } }
@Override public void onMatch(RelOptRuleCall call) { final HiveSortLimit sortLimit = call.rel(0); // We remove the limit operator call.transformTo(sortLimit.getInput()); }
@Override public boolean matches(final RelOptRuleCall call) { // Subquery must be a groupBy, so stage must be >= AGGREGATE. final DruidRel druidRel = call.rel(call.getRelList().size() - 1); return druidRel.getPartialDruidQuery().stage().compareTo(PartialDruidQuery.Stage.AGGREGATE) >= 0; } }
@Override public boolean matches(RelOptRuleCall call) { final Filter filter = call.rel(0); final RelNode filterChild = call.rel(1); // If the filter is already on top of a TableScan, // we can bail out if (filterChild instanceof TableScan) { return false; } HiveRulesRegistry registry = call.getPlanner().getContext().unwrap(HiveRulesRegistry.class); // If this operator has been visited already by the rule, // we do not need to apply the optimization if (registry != null && registry.getVisited(this).contains(filter)) { return false; } return true; }
if (!joinInfo.rightSet().equals( ImmutableBitSet.range(aggregate.getGroupCount()))) { call.transformTo(topOperator.copy(topOperator.getTraitSet(), ImmutableList.of(left))); return; final List<Integer> newRightKeyBuilder = Lists.newArrayList(); final List<Integer> aggregateKeys = aggregate.getGroupSet().asList(); for (int key : joinInfo.rightKeys) { Join rightJoin = (Join)(((HepRelVertex)aggregate.getInput()).getCurrentRel()); List<RexNode> projects = new ArrayList<>(); for(int i=0; i<rightJoin.getRowType().getFieldCount(); i++){ projects.add(rexBuilder.makeInputRef(rightJoin, i)); RelNode topProject = call.builder().push(rightJoin).project(projects, rightJoin.getRowType().getFieldNames(), true).build(); semi = call.builder().push(left).push(topProject).semiJoin(newCondition).build(); } else { semi = call.builder().push(left).push(aggregate.getInput()).semiJoin(newCondition).build(); call.transformTo(topOperator.copy(topOperator.getTraitSet(), ImmutableList.of(semi)));
public void onMatch(RelOptRuleCall call) { final LogicalCorrelate correlate = call.rel(0); final RelNode left = call.rel(1); final Project aggOutputProject = call.rel(2); final Aggregate aggregate = call.rel(3); final Project aggInputProject = call.rel(4); RelNode right = call.rel(5); final RelOptCluster cluster = correlate.getCluster(); setCurrent(call.getPlanner().getRoot(), correlate); List<RexFieldAccess> correlatedJoinKeys = Lists.newArrayList(); final RelMetadataQuery mq = call.getMetadataQuery(); if (!RelMdUtil.areColumnsDefinitelyUniqueWhenNullsFiltered(mq, left, correlatedInputRefJoinKeys)) { final RelMetadataQuery mq = call.getMetadataQuery(); if (!RelMdUtil.areColumnsDefinitelyUnique(mq, left, allCols)) { int nullIndicatorPos = join.getRowType().getFieldCount() - 1; cluster.getTypeFactory().createTypeWithNullability( newAggregate, newAggOutputProjectList, null, false, relBuilder); call.transformTo(newAggOutputProject);
public void onMatch(RelOptRuleCall call) { final LogicalCorrelate correlate = call.rel(0); final RelNode left = call.rel(1); final Aggregate aggregate = call.rel(2); final Project project = call.rel(3); RelNode right = call.rel(4); final RelOptCluster cluster = correlate.getCluster(); setCurrent(call.getPlanner().getRoot(), correlate); if ((!aggregate.getGroupSet().isEmpty()) || (aggregate.getAggCallList().size() != 1) || !(aggregate.getAggCallList().get(0).getAggregation() final RelMetadataQuery mq = call.getMetadataQuery(); if (!RelMdUtil.areColumnsDefinitelyUniqueWhenNullsFiltered(mq, right, rightJoinKeys)) { left.getRowType().getFieldCount() + rightJoinKeys.get(0).getIndex(); } else if (cm.mapRefRelToCorRef.containsKey(project)) { ImmutableList.of( Pair.<RexNode, String>of( rexBuilder.makeLiteral(true), "nullIndicator"))); projectJoinOutputWithNullability(join, project, nullIndicatorPos); call.transformTo(newProject);
public void onMatch(RelOptRuleCall call) { final HiveIntersect hiveIntersect = call.rel(0); final RexBuilder rexBuilder = cluster.getRexBuilder(); int numOfBranch = hiveIntersect.getInputs().size(); Builder<RelNode> bldr = new ImmutableList.Builder<RelNode>(); gbChildProjLst.add(rexBuilder.makeBigintLiteral(new BigDecimal(1))); final ImmutableBitSet groupSet = ImmutableBitSet.of(groupSetPositions); TypeInfoFactory.longTypeInfo, input.getRowType().getFieldList().size(), aggFnRetType); aggregateCalls.add(aggregateCall); int cInd = union.getRowType().getFieldList().size() - 1; final ImmutableBitSet groupSet = ImmutableBitSet.of(groupSetPositions); RexInputRef ref = rexBuilder.makeInputRef(aggregateRel, countInd); projectOutColumnPositions.add(filterRel.getRowType().getFieldList().size() - 1); try { call.transformTo(HiveCalciteUtil.createProjectWithoutColumn(filterRel,projectOutColumnPositions)); } catch (CalciteSemanticException e) { LOG.debug(e.toString()); call.transformTo(HiveCalciteUtil .createProjectWithoutColumn(udtf, projectOutColumnPositions)); } catch (SemanticException e) {
@Override public void onMatch(RelOptRuleCall call) { final Project project = call.rel(0); final RelMetadataQuery mq = call.getMetadataQuery(); final RelOptPredicateList predicates = mq.getPulledUpPredicates(project.getInput()); final List<RexNode> expList = Lists.newArrayList(project.getProjects()); if (reduceExpressions(project, expList, predicates, false, matchNullability)) { call.transformTo( call.builder() .push(project.getInput()) .project(expList, project.getRowType().getFieldNames()) .build()); // New plan is absolutely better than old plan. call.getPlanner().setImportance(project, 0.0); } } }
public void onMatch(RelOptRuleCall call) { final LogicalCorrelate correlate = call.rel(0); final RelNode left = call.rel(1); final Project aggOutputProject; final Aggregate aggregate; if (flavor) { aggOutputProject = call.rel(2); aggregate = call.rel(3); } else { aggregate = call.rel(2); // Create identity projection final List<Pair<RexNode, String>> projects = Lists.newArrayList(); final List<RelDataTypeField> fields = aggregate.getRowType().getFieldList(); for (int i = 0; i < fields.size(); i++) { projects.add(RexInputRef.of2(projects.size(), fields)); } aggOutputProject = (Project) RelOptUtil.createProject( aggregate, Pair.left(projects), Pair.right(projects), false, relBuilder); } onMatch2(call, correlate, left, aggOutputProject, aggregate); }
@Override public void onMatch(RelOptRuleCall call) { final RelBuilder relBuilder = call.builder(); final Aggregate aggRel = (Aggregate) call.rel(0); final RexBuilder rexBuilder = aggRel.getCluster().getRexBuilder(); final List<Integer> nullableArgs = new ArrayList<>(args.size()); for (int arg : args) { if (aggRel.getInput().getRowType().getFieldList().get(arg).getType().isNullable()) { nullableArgs.add(arg); newAggCalls); if (identity) { call.transformTo(newAggregate); } else { final int offset = aggRel.getGroupCount() + aggRel.getIndicatorCount(); final List<RexNode> projList = Lists.newArrayList(); for (int i = 0; i < offset; ++i) { projList.add( rexBuilder.makeInputRef( aggRel.getRowType().getFieldList().get(i).getType(), i)); for (int i = offset; i < aggRel.getRowType().getFieldCount(); ++i) { projList.add( rexBuilder.makeInputRef( aggRel.getRowType().getFieldList().get(i).getType(), indexes.get(i-offset))); call.transformTo(relBuilder.push(newAggregate).project(projList).build());
@Override public void onMatch(RelOptRuleCall call) { final Filter filter = call.rel(0); final List<RexNode> expList = Lists.newArrayList(filter.getCondition()); RexNode newConditionExp; boolean reduced; final RelMetadataQuery mq = call.getMetadataQuery(); final RelOptPredicateList predicates = mq.getPulledUpPredicates(filter.getInput()); if (newConditionExp.isAlwaysTrue()) { call.transformTo( filter.getInput()); } else if (reduced) { if (RexUtil.isNullabilityCast(filter.getCluster().getTypeFactory(), newConditionExp)) { newConditionExp = ((RexCall) newConditionExp).getOperands().get(0); if(newConditionExp.getType().getSqlTypeName() == SqlTypeName.NULL) { newConditionExp = call.builder().cast(newConditionExp, SqlTypeName.BOOLEAN); call.transformTo(call.builder(). push(filter.getInput()).filter(newConditionExp).build()); } else { call.getPlanner().setImportance(filter, 0.0);
RelOptRuleCall ruleCall, Aggregate oldAggRel) { RexBuilder rexBuilder = oldAggRel.getCluster().getRexBuilder(); final int indicatorCount = oldAggRel.getIndicatorCount(); final List<AggregateCall> newCalls = Lists.newArrayList(); final Map<AggregateCall, RexNode> aggCallMapping = Maps.newHashMap(); final List<RexNode> projList = Lists.newArrayList(); rexBuilder.makeInputRef( getFieldType(oldAggRel, i), i)); final RelBuilder relBuilder = ruleCall.builder(); relBuilder.push(oldAggRel.getInput()); final List<RexNode> inputExprs = new ArrayList<>(relBuilder.fields()); relBuilder.project(projList, oldAggRel.getRowType().getFieldNames()) .convert(oldAggRel.getRowType(), false); ruleCall.transformTo(relBuilder.build());
@Override public void onMatch(RelOptRuleCall call) { final Aggregate aggregate = call.rel(0); final Join join = call.rel(1); final RexBuilder rexBuilder = aggregate.getCluster().getRexBuilder(); final RelBuilder relBuilder = call.builder(); final RelMetadataQuery mq = call.getMetadataQuery(); final ImmutableBitSet keyColumns = keyColumns(aggregateColumns, mq.getPulledUpPredicates(join).pulledUpPredicates); if (!nonEquiConj.isAlwaysTrue()) { return; call1 = splitter.split(aggCall.e, mapping); } else { call1 = splitter.other(rexBuilder.getTypeFactory(), aggCall.e); belowOffset += side.newInput.getRowType().getFieldCount(); sides.add(side); join.getRowType().getFieldCount(), belowOffset); final RexNode newCondition = RelOptCost beforeCost = mq.getCumulativeCost(aggregate); if (afterCost.isLt(beforeCost)) { call.transformTo(r);
@Override public void onMatch(RelOptRuleCall call) { final Join join = call.rel(0); final List<RexNode> expList = Lists.newArrayList(join.getCondition()); final int fieldCount = join.getLeft().getRowType().getFieldCount(); final RelMetadataQuery mq = call.getMetadataQuery(); final RelOptPredicateList leftPredicates = mq.getPulledUpPredicates(join.getLeft()); final RelOptPredicateList rightPredicates = mq.getPulledUpPredicates(join.getRight()); final RexBuilder rexBuilder = join.getCluster().getRexBuilder(); final RelOptPredicateList predicates = leftPredicates.union(rexBuilder, call.transformTo( join.copy( join.getTraitSet(), call.getPlanner().setImportance(join, 0.0);
@Override public void onMatch(RelOptRuleCall call) { final Project proj = call.rel(0); final ScanCrel scan = call.rel(1); ProjectPushInfo columnInfo = PrelUtil.getColumns(scan.getRowType(), proj.getProjects()); // get TableBase, either wrapped in RelOptTable, or TranslatableTable. TableBase table = scan.getTable().unwrap(TableBase.class); if (columnInfo == null || columnInfo.isStarQuery()) { return; } ScanCrel newScan = scan.cloneWithProject(columnInfo.columns); List<RexNode> newProjects = Lists.newArrayList(); for (RexNode n : proj.getChildExps()) { newProjects.add(n.accept(columnInfo.getInputRewriter())); } final RelBuilder relBuilder = relBuilderFactory.create(proj.getCluster(), null); relBuilder.push(newScan); relBuilder.project(newProjects, proj.getRowType().getFieldNames()); final RelNode newProj = relBuilder.build(); if (newProj instanceof Project && ProjectRemoveRule.isTrivial((Project) newProj) && newScan.getRowType().getFullTypeString().equals(newProj.getRowType().getFullTypeString())) { call.transformTo(newScan); } else { if(newScan.getProjectedColumns().equals(scan.getProjectedColumns())) { // no point in doing a pushdown that doesn't change anything. return; } call.transformTo(newProj); } }
public void onMatch(RelOptRuleCall call) { Aggregate singleAggregate = call.rel(0); Project project = call.rel(1); Aggregate aggregate = call.rel(2); if ((!singleAggregate.getGroupSet().isEmpty()) || (singleAggregate.getAggCallList().size() != 1) || !(singleAggregate.getAggCallList().get(0).getAggregation() if (!aggregate.getGroupSet().isEmpty()) { return; ImmutableList.of(rexBuilder.makeCast( cluster.getTypeFactory().createTypeWithNullability(projExprs.get(0).getType(), true), projExprs.get(0))), null, false, relBuilder); call.transformTo(newProject);
public void onMatch(RelOptRuleCall call) { final HiveFilter filter = call.rel(0); final HiveSortLimit sort = call.rel(1); final RelNode newFilter = filter.copy(sort.getInput().getTraitSet(), ImmutableList.<RelNode>of(sort.getInput())); final HiveSortLimit newSort = sort.copy(sort.getTraitSet(), newFilter, sort.collation, sort.offset, sort.fetch); call.transformTo(newSort); }