presto-main/src/main/java/io/prestosql/sql/planner/optimizations/TransformQuantifiedComparisonApplyToCorrelatedJoin.java/TransformQuantifiedComparisonApplyToCorrelatedJoin/rewriteQuantifiedApplyNode
class TransformQuantifiedComparisonApplyToCorrelatedJoin:        private PlanNode rewriteQuantifiedApplyNode(ApplyNode node, QuantifiedComparisonExpression quantifiedComparison, RewriteContext<PlanNode> context)
        {
            PlanNode subqueryPlan = context.rewrite(node.getSubquery());

            Symbol outputColumn = getOnlyElement(subqueryPlan.getOutputSymbols());
            Type outputColumnType = types.get(outputColumn);
            checkState(outputColumnType.isOrderable(), "Subquery result type must be orderable");

            Symbol minValue = symbolAllocator.newSymbol(MIN.toString(), outputColumnType);
            Symbol maxValue = symbolAllocator.newSymbol(MAX.toString(), outputColumnType);
            Symbol countAllValue = symbolAllocator.newSymbol("count_all", BigintType.BIGINT);
            Symbol countNonNullValue = symbolAllocator.newSymbol("count_non_null", BigintType.BIGINT);

            List<Expression> outputColumnReferences = ImmutableList.of(outputColumn.toSymbolReference());

            subqueryPlan = new AggregationNode(
                    idAllocator.getNextId(),
                    subqueryPlan,
                    ImmutableMap.of(
                            minValue, new Aggregation(
                                    metadata.resolveFunction(MIN, fromTypes(outputColumnType)),
                                    outputColumnReferences,
                                    false,
                                    Optional.empty(),
                                    Optional.empty(),
                                    Optional.empty()),
                            maxValue, new Aggregation(
                                    metadata.resolveFunction(MAX, fromTypes(outputColumnType)),
                                    outputColumnReferences,
                                    false,
                                    Optional.empty(),
                                    Optional.empty(),
                                    Optional.empty()),
                            countAllValue, new Aggregation(
                                    metadata.resolveFunction(COUNT, emptyList()),
                                    ImmutableList.of(),
                                    false,
                                    Optional.empty(),
                                    Optional.empty(),
                                    Optional.empty()),
                            countNonNullValue, new Aggregation(
                                    metadata.resolveFunction(COUNT, fromTypes(outputColumnType)),
                                    outputColumnReferences,
                                    false,
                                    Optional.empty(),
                                    Optional.empty(),
                                    Optional.empty())),
                    globalAggregation(),
                    ImmutableList.of(),
                    AggregationNode.Step.SINGLE,
                    Optional.empty(),
                    Optional.empty());

            PlanNode join = new CorrelatedJoinNode(
                    node.getId(),
                    context.rewrite(node.getInput()),
                    subqueryPlan,
                    node.getCorrelation(),
                    CorrelatedJoinNode.Type.INNER,
                    TRUE_LITERAL,
                    node.getOriginSubquery());

            Expression valueComparedToSubquery = rewriteUsingBounds(quantifiedComparison, minValue, maxValue, countAllValue, countNonNullValue);

            Symbol quantifiedComparisonSymbol = getOnlyElement(node.getSubqueryAssignments().getSymbols());

            return projectExpressions(join, Assignments.of(quantifiedComparisonSymbol, valueComparedToSubquery));
        }