Search in sources :

Example 1 with GeneratedRecordComparator

use of org.apache.flink.table.runtime.generated.GeneratedRecordComparator in project flink by apache.

the class StreamExecTemporalSort method createSortProcTime.

/**
 * Create Sort logic based on processing time.
 */
private Transformation<RowData> createSortProcTime(RowType inputType, Transformation<RowData> inputTransform, ExecNodeConfig config) {
    // if the order has secondary sorting fields in addition to the proctime
    if (sortSpec.getFieldSize() > 1) {
        // skip the first field which is the proctime field and would be ordered by timer.
        SortSpec specExcludeTime = sortSpec.createSubSortSpec(1);
        GeneratedRecordComparator rowComparator = ComparatorCodeGenerator.gen(config.getTableConfig(), "ProcTimeSortComparator", inputType, specExcludeTime);
        ProcTimeSortOperator sortOperator = new ProcTimeSortOperator(InternalTypeInfo.of(inputType), rowComparator);
        OneInputTransformation<RowData, RowData> transform = ExecNodeUtil.createOneInputTransformation(inputTransform, createTransformationMeta(TEMPORAL_SORT_TRANSFORMATION, config), sortOperator, InternalTypeInfo.of(inputType), inputTransform.getParallelism());
        // as input node is singleton exchange, its parallelism is 1.
        if (inputsContainSingleton()) {
            transform.setParallelism(1);
            transform.setMaxParallelism(1);
        }
        EmptyRowDataKeySelector selector = EmptyRowDataKeySelector.INSTANCE;
        transform.setStateKeySelector(selector);
        transform.setStateKeyType(selector.getProducedType());
        return transform;
    } else {
        // if the order is done only on proctime we only need to forward the elements
        return inputTransform;
    }
}
Also used : RowData(org.apache.flink.table.data.RowData) ProcTimeSortOperator(org.apache.flink.table.runtime.operators.sort.ProcTimeSortOperator) GeneratedRecordComparator(org.apache.flink.table.runtime.generated.GeneratedRecordComparator) EmptyRowDataKeySelector(org.apache.flink.table.runtime.keyselector.EmptyRowDataKeySelector) SortSpec(org.apache.flink.table.planner.plan.nodes.exec.spec.SortSpec)

Example 2 with GeneratedRecordComparator

use of org.apache.flink.table.runtime.generated.GeneratedRecordComparator in project flink by apache.

the class StreamExecTemporalSort method createSortRowTime.

/**
 * Create Sort logic based on row time.
 */
private Transformation<RowData> createSortRowTime(RowType inputType, Transformation<RowData> inputTransform, ExecNodeConfig config) {
    GeneratedRecordComparator rowComparator = null;
    if (sortSpec.getFieldSize() > 1) {
        // skip the first field which is the rowtime field and would be ordered by timer.
        SortSpec specExcludeTime = sortSpec.createSubSortSpec(1);
        rowComparator = ComparatorCodeGenerator.gen(config.getTableConfig(), "RowTimeSortComparator", inputType, specExcludeTime);
    }
    RowTimeSortOperator sortOperator = new RowTimeSortOperator(InternalTypeInfo.of(inputType), sortSpec.getFieldSpec(0).getFieldIndex(), rowComparator);
    OneInputTransformation<RowData, RowData> transform = ExecNodeUtil.createOneInputTransformation(inputTransform, createTransformationMeta(TEMPORAL_SORT_TRANSFORMATION, config), sortOperator, InternalTypeInfo.of(inputType), inputTransform.getParallelism());
    if (inputsContainSingleton()) {
        transform.setParallelism(1);
        transform.setMaxParallelism(1);
    }
    EmptyRowDataKeySelector selector = EmptyRowDataKeySelector.INSTANCE;
    transform.setStateKeySelector(selector);
    transform.setStateKeyType(selector.getProducedType());
    return transform;
}
Also used : RowData(org.apache.flink.table.data.RowData) RowTimeSortOperator(org.apache.flink.table.runtime.operators.sort.RowTimeSortOperator) GeneratedRecordComparator(org.apache.flink.table.runtime.generated.GeneratedRecordComparator) EmptyRowDataKeySelector(org.apache.flink.table.runtime.keyselector.EmptyRowDataKeySelector) SortSpec(org.apache.flink.table.planner.plan.nodes.exec.spec.SortSpec)

Example 3 with GeneratedRecordComparator

use of org.apache.flink.table.runtime.generated.GeneratedRecordComparator in project flink by apache.

the class StreamExecSort method translateToPlanInternal.

@SuppressWarnings("unchecked")
@Override
protected Transformation<RowData> translateToPlanInternal(PlannerBase planner, ExecNodeConfig config) {
    if (!config.get(InternalConfigOptions.TABLE_EXEC_NON_TEMPORAL_SORT_ENABLED)) {
        throw new TableException("Sort on a non-time-attribute field is not supported.");
    }
    ExecEdge inputEdge = getInputEdges().get(0);
    RowType inputType = (RowType) inputEdge.getOutputType();
    // sort code gen
    GeneratedRecordComparator rowComparator = ComparatorCodeGenerator.gen(config.getTableConfig(), "StreamExecSortComparator", inputType, sortSpec);
    StreamSortOperator sortOperator = new StreamSortOperator(InternalTypeInfo.of(inputType), rowComparator);
    Transformation<RowData> inputTransform = (Transformation<RowData>) inputEdge.translateToPlan(planner);
    return ExecNodeUtil.createOneInputTransformation(inputTransform, createTransformationMeta(SORT_TRANSFORMATION, config), sortOperator, InternalTypeInfo.of(inputType), inputTransform.getParallelism());
}
Also used : TableException(org.apache.flink.table.api.TableException) RowData(org.apache.flink.table.data.RowData) Transformation(org.apache.flink.api.dag.Transformation) ExecEdge(org.apache.flink.table.planner.plan.nodes.exec.ExecEdge) RowType(org.apache.flink.table.types.logical.RowType) StreamSortOperator(org.apache.flink.table.runtime.operators.sort.StreamSortOperator) GeneratedRecordComparator(org.apache.flink.table.runtime.generated.GeneratedRecordComparator)

Example 4 with GeneratedRecordComparator

use of org.apache.flink.table.runtime.generated.GeneratedRecordComparator in project flink by apache.

the class BatchExecOverAggregate method createOverWindowFrames.

private List<OverWindowFrame> createOverWindowFrames(FlinkRelBuilder relBuilder, ExecNodeConfig config, RowType inputType, SortSpec sortSpec, RowType inputTypeWithConstants) {
    final List<OverWindowFrame> windowFrames = new ArrayList<>();
    for (GroupSpec group : overSpec.getGroups()) {
        OverWindowMode mode = inferGroupMode(group);
        if (mode == OverWindowMode.OFFSET) {
            for (AggregateCall aggCall : group.getAggCalls()) {
                AggregateInfoList aggInfoList = AggregateUtil.transformToBatchAggregateInfoList(inputTypeWithConstants, JavaScalaConversionUtil.toScala(Collections.singletonList(aggCall)), new boolean[] { true }, /* needRetraction = true, See LeadLagAggFunction */
                sortSpec.getFieldIndices());
                AggsHandlerCodeGenerator generator = new AggsHandlerCodeGenerator(new CodeGeneratorContext(config.getTableConfig()), relBuilder, JavaScalaConversionUtil.toScala(inputType.getChildren()), // copyInputField
                false);
                // over agg code gen must pass the constants
                GeneratedAggsHandleFunction genAggsHandler = generator.needAccumulate().needRetract().withConstants(JavaScalaConversionUtil.toScala(getConstants())).generateAggsHandler("BoundedOverAggregateHelper", aggInfoList);
                // LEAD is behind the currentRow, so we need plus offset.
                // LAG is in front of the currentRow, so we need minus offset.
                long flag = aggCall.getAggregation().kind == SqlKind.LEAD ? 1L : -1L;
                final Long offset;
                final OffsetOverFrame.CalcOffsetFunc calcOffsetFunc;
                // The second arg mean the offset arg index for leag/lag function, default is 1.
                if (aggCall.getArgList().size() >= 2) {
                    int constantIndex = aggCall.getArgList().get(1) - overSpec.getOriginalInputFields();
                    if (constantIndex < 0) {
                        offset = null;
                        int rowIndex = aggCall.getArgList().get(1);
                        switch(inputType.getTypeAt(rowIndex).getTypeRoot()) {
                            case BIGINT:
                                calcOffsetFunc = row -> row.getLong(rowIndex) * flag;
                                break;
                            case INTEGER:
                                calcOffsetFunc = row -> (long) row.getInt(rowIndex) * flag;
                                break;
                            case SMALLINT:
                                calcOffsetFunc = row -> (long) row.getShort(rowIndex) * flag;
                                break;
                            default:
                                throw new RuntimeException("The column type must be in long/int/short.");
                        }
                    } else {
                        long constantOffset = getConstants().get(constantIndex).getValueAs(Long.class);
                        offset = constantOffset * flag;
                        calcOffsetFunc = null;
                    }
                } else {
                    offset = flag;
                    calcOffsetFunc = null;
                }
                windowFrames.add(new OffsetOverFrame(genAggsHandler, offset, calcOffsetFunc));
            }
        } else {
            AggregateInfoList aggInfoList = AggregateUtil.transformToBatchAggregateInfoList(// inputSchema.relDataType
            inputTypeWithConstants, JavaScalaConversionUtil.toScala(group.getAggCalls()), // aggCallNeedRetractions
            null, sortSpec.getFieldIndices());
            AggsHandlerCodeGenerator generator = new AggsHandlerCodeGenerator(new CodeGeneratorContext(config.getTableConfig()), relBuilder, JavaScalaConversionUtil.toScala(inputType.getChildren()), // copyInputField
            false);
            // over agg code gen must pass the constants
            GeneratedAggsHandleFunction genAggsHandler = generator.needAccumulate().withConstants(JavaScalaConversionUtil.toScala(getConstants())).generateAggsHandler("BoundedOverAggregateHelper", aggInfoList);
            RowType valueType = generator.valueType();
            final OverWindowFrame frame;
            switch(mode) {
                case RANGE:
                    if (isUnboundedWindow(group)) {
                        frame = new UnboundedOverWindowFrame(genAggsHandler, valueType);
                    } else if (isUnboundedPrecedingWindow(group)) {
                        GeneratedRecordComparator genBoundComparator = createBoundComparator(relBuilder, config, sortSpec, group.getUpperBound(), false, inputType);
                        frame = new RangeUnboundedPrecedingOverFrame(genAggsHandler, genBoundComparator);
                    } else if (isUnboundedFollowingWindow(group)) {
                        GeneratedRecordComparator genBoundComparator = createBoundComparator(relBuilder, config, sortSpec, group.getLowerBound(), true, inputType);
                        frame = new RangeUnboundedFollowingOverFrame(valueType, genAggsHandler, genBoundComparator);
                    } else if (isSlidingWindow(group)) {
                        GeneratedRecordComparator genLeftBoundComparator = createBoundComparator(relBuilder, config, sortSpec, group.getLowerBound(), true, inputType);
                        GeneratedRecordComparator genRightBoundComparator = createBoundComparator(relBuilder, config, sortSpec, group.getUpperBound(), false, inputType);
                        frame = new RangeSlidingOverFrame(inputType, valueType, genAggsHandler, genLeftBoundComparator, genRightBoundComparator);
                    } else {
                        throw new TableException("This should not happen.");
                    }
                    break;
                case ROW:
                    if (isUnboundedWindow(group)) {
                        frame = new UnboundedOverWindowFrame(genAggsHandler, valueType);
                    } else if (isUnboundedPrecedingWindow(group)) {
                        frame = new RowUnboundedPrecedingOverFrame(genAggsHandler, OverAggregateUtil.getLongBoundary(overSpec, group.getUpperBound()));
                    } else if (isUnboundedFollowingWindow(group)) {
                        frame = new RowUnboundedFollowingOverFrame(valueType, genAggsHandler, OverAggregateUtil.getLongBoundary(overSpec, group.getLowerBound()));
                    } else if (isSlidingWindow(group)) {
                        frame = new RowSlidingOverFrame(inputType, valueType, genAggsHandler, OverAggregateUtil.getLongBoundary(overSpec, group.getLowerBound()), OverAggregateUtil.getLongBoundary(overSpec, group.getUpperBound()));
                    } else {
                        throw new TableException("This should not happen.");
                    }
                    break;
                case INSENSITIVE:
                    frame = new InsensitiveOverFrame(genAggsHandler);
                    break;
                default:
                    throw new TableException("This should not happen.");
            }
            windowFrames.add(frame);
        }
    }
    return windowFrames;
}
Also used : AggregateInfoList(org.apache.flink.table.planner.plan.utils.AggregateInfoList) ArrayList(java.util.ArrayList) AggsHandlerCodeGenerator(org.apache.flink.table.planner.codegen.agg.AggsHandlerCodeGenerator) RowType(org.apache.flink.table.types.logical.RowType) RowUnboundedFollowingOverFrame(org.apache.flink.table.runtime.operators.over.frame.RowUnboundedFollowingOverFrame) RangeUnboundedPrecedingOverFrame(org.apache.flink.table.runtime.operators.over.frame.RangeUnboundedPrecedingOverFrame) RowUnboundedPrecedingOverFrame(org.apache.flink.table.runtime.operators.over.frame.RowUnboundedPrecedingOverFrame) RowSlidingOverFrame(org.apache.flink.table.runtime.operators.over.frame.RowSlidingOverFrame) InsensitiveOverFrame(org.apache.flink.table.runtime.operators.over.frame.InsensitiveOverFrame) TableException(org.apache.flink.table.api.TableException) CodeGeneratorContext(org.apache.flink.table.planner.codegen.CodeGeneratorContext) OffsetOverFrame(org.apache.flink.table.runtime.operators.over.frame.OffsetOverFrame) GeneratedAggsHandleFunction(org.apache.flink.table.runtime.generated.GeneratedAggsHandleFunction) RangeSlidingOverFrame(org.apache.flink.table.runtime.operators.over.frame.RangeSlidingOverFrame) UnboundedOverWindowFrame(org.apache.flink.table.runtime.operators.over.frame.UnboundedOverWindowFrame) UnboundedOverWindowFrame(org.apache.flink.table.runtime.operators.over.frame.UnboundedOverWindowFrame) OverWindowFrame(org.apache.flink.table.runtime.operators.over.frame.OverWindowFrame) AggregateCall(org.apache.calcite.rel.core.AggregateCall) GroupSpec(org.apache.flink.table.planner.plan.nodes.exec.spec.OverSpec.GroupSpec) RangeUnboundedFollowingOverFrame(org.apache.flink.table.runtime.operators.over.frame.RangeUnboundedFollowingOverFrame) GeneratedRecordComparator(org.apache.flink.table.runtime.generated.GeneratedRecordComparator)

Example 5 with GeneratedRecordComparator

use of org.apache.flink.table.runtime.generated.GeneratedRecordComparator in project flink by apache.

the class BatchExecSortLimit method translateToPlanInternal.

@SuppressWarnings("unchecked")
@Override
protected Transformation<RowData> translateToPlanInternal(PlannerBase planner, ExecNodeConfig config) {
    if (limitEnd == Long.MAX_VALUE) {
        throw new TableException("Not support limitEnd is max value now!");
    }
    ExecEdge inputEdge = getInputEdges().get(0);
    Transformation<RowData> inputTransform = (Transformation<RowData>) inputEdge.translateToPlan(planner);
    RowType inputType = (RowType) inputEdge.getOutputType();
    // generate comparator
    GeneratedRecordComparator genComparator = ComparatorCodeGenerator.gen(config.getTableConfig(), "SortLimitComparator", inputType, sortSpec);
    // TODO If input is ordered, there is no need to use the heap.
    SortLimitOperator operator = new SortLimitOperator(isGlobal, limitStart, limitEnd, genComparator);
    return ExecNodeUtil.createOneInputTransformation(inputTransform, createTransformationName(config), createTransformationDescription(config), SimpleOperatorFactory.of(operator), InternalTypeInfo.of(inputType), inputTransform.getParallelism());
}
Also used : TableException(org.apache.flink.table.api.TableException) RowData(org.apache.flink.table.data.RowData) Transformation(org.apache.flink.api.dag.Transformation) ExecEdge(org.apache.flink.table.planner.plan.nodes.exec.ExecEdge) RowType(org.apache.flink.table.types.logical.RowType) GeneratedRecordComparator(org.apache.flink.table.runtime.generated.GeneratedRecordComparator) SortLimitOperator(org.apache.flink.table.runtime.operators.sort.SortLimitOperator)

Aggregations

GeneratedRecordComparator (org.apache.flink.table.runtime.generated.GeneratedRecordComparator)10 RowData (org.apache.flink.table.data.RowData)8 RowType (org.apache.flink.table.types.logical.RowType)6 Transformation (org.apache.flink.api.dag.Transformation)5 TableException (org.apache.flink.table.api.TableException)5 ExecEdge (org.apache.flink.table.planner.plan.nodes.exec.ExecEdge)5 SortSpec (org.apache.flink.table.planner.plan.nodes.exec.spec.SortSpec)5 ArrayList (java.util.ArrayList)2 OneInputTransformation (org.apache.flink.streaming.api.transformations.OneInputTransformation)2 CodeGeneratorContext (org.apache.flink.table.planner.codegen.CodeGeneratorContext)2 AggsHandlerCodeGenerator (org.apache.flink.table.planner.codegen.agg.AggsHandlerCodeGenerator)2 GroupSpec (org.apache.flink.table.planner.plan.nodes.exec.spec.OverSpec.GroupSpec)2 AggregateInfoList (org.apache.flink.table.planner.plan.utils.AggregateInfoList)2 GeneratedAggsHandleFunction (org.apache.flink.table.runtime.generated.GeneratedAggsHandleFunction)2 EmptyRowDataKeySelector (org.apache.flink.table.runtime.keyselector.EmptyRowDataKeySelector)2 RowDataKeySelector (org.apache.flink.table.runtime.keyselector.RowDataKeySelector)2 OverWindowFrame (org.apache.flink.table.runtime.operators.over.frame.OverWindowFrame)2 UnboundedOverWindowFrame (org.apache.flink.table.runtime.operators.over.frame.UnboundedOverWindowFrame)2 ZoneId (java.time.ZoneId)1 AggregateCall (org.apache.calcite.rel.core.AggregateCall)1