@Override public boolean shapeMatches(PlanNode node) { if (!(node instanceof SpatialJoinNode)) { return false; } SpatialJoinNode joinNode = (SpatialJoinNode) node; return joinNode.getType() == type; }
@Override public StreamProperties visitSpatialJoin(SpatialJoinNode node, List<StreamProperties> inputProperties) { StreamProperties leftProperties = inputProperties.get(0); switch (node.getType()) { case INNER: case LEFT: return leftProperties.translate(column -> PropertyDerivations.filterIfMissing(node.getOutputSymbols(), column)); default: throw new IllegalArgumentException("Unsupported spatial join type: " + node.getType()); } }
@Override protected Optional<PlanNodeStatsEstimate> doCalculate(SpatialJoinNode node, StatsProvider sourceStats, Lookup lookup, Session session, TypeProvider types) { PlanNodeStatsEstimate leftStats = sourceStats.getStats(node.getLeft()); PlanNodeStatsEstimate rightStats = sourceStats.getStats(node.getRight()); PlanNodeStatsEstimate crossJoinStats = crossJoinStats(node, leftStats, rightStats); switch (node.getType()) { case INNER: return Optional.of(statsCalculator.filterStats(crossJoinStats, node.getFilter(), session, types)); case LEFT: return Optional.of(PlanNodeStatsEstimate.unknown()); default: throw new IllegalArgumentException("Unknown spatial join type: " + node.getType()); } }
private OperatorFactory createSpatialLookupJoin(SpatialJoinNode node, PlanNode probeNode, PhysicalOperation probeSource, Symbol probeSymbol, PagesSpatialIndexFactory pagesSpatialIndexFactory, LocalExecutionPlanContext context) { List<Type> probeTypes = probeSource.getTypes(); List<Symbol> probeOutputSymbols = node.getOutputSymbols().stream() .filter(symbol -> probeNode.getOutputSymbols().contains(symbol)) .collect(toImmutableList()); List<Integer> probeOutputChannels = ImmutableList.copyOf(getChannelsForSymbols(probeOutputSymbols, probeSource.getLayout())); Function<Symbol, Integer> probeChannelGetter = channelGetter(probeSource); int probeChannel = probeChannelGetter.apply(probeSymbol); Optional<Integer> partitionChannel = node.getLeftPartitionSymbol().map(probeChannelGetter::apply); return new SpatialJoinOperatorFactory( context.getNextOperatorId(), node.getId(), node.getType(), probeTypes, probeOutputChannels, probeChannel, partitionChannel, pagesSpatialIndexFactory); }
@Override public PlanNode visitSpatialJoin(SpatialJoinNode node, RewriteContext<Set<Symbol>> context) { Set<Symbol> requiredInputs = ImmutableSet.<Symbol>builder() .addAll(SymbolsExtractor.extractUnique(node.getFilter())) .addAll(context.get()) .build(); ImmutableSet.Builder<Symbol> leftInputs = ImmutableSet.builder(); node.getLeftPartitionSymbol().map(leftInputs::add); ImmutableSet.Builder<Symbol> rightInputs = ImmutableSet.builder(); node.getRightPartitionSymbol().map(rightInputs::add); PlanNode left = context.rewrite(node.getLeft(), leftInputs.addAll(requiredInputs).build()); PlanNode right = context.rewrite(node.getRight(), rightInputs.addAll(requiredInputs).build()); List<Symbol> outputSymbols = node.getOutputSymbols().stream() .filter(context.get()::contains) .distinct() .collect(toImmutableList()); return new SpatialJoinNode(node.getId(), node.getType(), left, right, outputSymbols, node.getFilter(), node.getLeftPartitionSymbol(), node.getRightPartitionSymbol(), node.getKdbTree()); }
@Override public Expression visitSpatialJoin(SpatialJoinNode node, Void context) { Expression leftPredicate = node.getLeft().accept(this, context); Expression rightPredicate = node.getRight().accept(this, context); switch (node.getType()) { case INNER: return combineConjuncts(ImmutableList.<Expression>builder() .add(pullExpressionThroughSymbols(leftPredicate, node.getOutputSymbols())) .add(pullExpressionThroughSymbols(rightPredicate, node.getOutputSymbols())) .build()); case LEFT: return combineConjuncts(ImmutableList.<Expression>builder() .add(pullExpressionThroughSymbols(leftPredicate, node.getOutputSymbols())) .addAll(pullNullableConjunctsThroughOuterJoin(extractConjuncts(rightPredicate), node.getOutputSymbols(), node.getRight().getOutputSymbols()::contains)) .build()); default: throw new IllegalArgumentException("Unsupported spatial join type: " + node.getType()); } }
@Override public ActualProperties visitSpatialJoin(SpatialJoinNode node, List<ActualProperties> inputProperties) { ActualProperties probeProperties = inputProperties.get(0); ActualProperties buildProperties = inputProperties.get(1); switch (node.getType()) { case INNER: probeProperties = probeProperties.translate(column -> filterIfMissing(node.getOutputSymbols(), column)); buildProperties = buildProperties.translate(column -> filterIfMissing(node.getOutputSymbols(), column)); Map<Symbol, NullableValue> constants = new HashMap<>(); constants.putAll(probeProperties.getConstants()); constants.putAll(buildProperties.getConstants()); return ActualProperties.builderFrom(probeProperties) .constants(constants) .build(); case LEFT: return ActualProperties.builderFrom(probeProperties.translate(column -> filterIfMissing(node.getOutputSymbols(), column))) .build(); default: throw new IllegalArgumentException("Unsupported spatial join type: " + node.getType()); } }
@Override public Void visitSpatialJoin(SpatialJoinNode node, Void context) { printNode(node, node.getType().getJoinLabel(), node.getFilter().toString(), NODE_COLORS.get(NodeType.JOIN)); node.getLeft().accept(this, context); node.getRight().accept(this, context); return null; }
@Override public Void visitSpatialJoin(SpatialJoinNode node, Integer indent) { print(indent, "- %s[%s] => [%s]", node.getType().getJoinLabel(), node.getFilter(), formatOutputs(node.getOutputSymbols())); print(indent + 2, "Distribution: %s", node.getDistributionType()); printPlanNodesStatsAndCost(indent + 2, node); printStats(indent + 2, node.getId()); node.getLeft().accept(this, indent + 1); node.getRight().accept(this, indent + 1); return null; }
@Override public PlanNode visitSpatialJoin(SpatialJoinNode node, RewriteContext<Void> context) { PlanNode left = context.rewrite(node.getLeft()); PlanNode right = context.rewrite(node.getRight()); return new SpatialJoinNode(node.getId(), node.getType(), left, right, canonicalizeAndDistinct(node.getOutputSymbols()), canonicalize(node.getFilter()), canonicalize(node.getLeftPartitionSymbol()), canonicalize(node.getRightPartitionSymbol()), node.getKdbTree()); }
if (node.getType() == SpatialJoinNode.Type.LEFT && canConvertOuterToInner(node.getRight().getOutputSymbols(), inheritedPredicate)) { node = new SpatialJoinNode(node.getId(), SpatialJoinNode.Type.INNER, node.getLeft(), node.getRight(), node.getOutputSymbols(), node.getFilter(), node.getLeftPartitionSymbol(), node.getRightPartitionSymbol(), node.getKdbTree()); Expression newJoinPredicate; switch (node.getType()) { case INNER: InnerJoinPushDownResult innerJoinPushDownResult = processInnerJoin( break; default: throw new IllegalArgumentException("Unsupported spatial join type: " + node.getType()); node.getType(), leftSource, rightSource,