public TreeTopKOperator topKOperatorTest3(
      Ordering timeOrdering, Ordering deviceOrdering, int limitValue) {
    ExecutorService instanceNotificationExecutor =
        IoTDBThreadPoolFactory.newFixedThreadPool(1, "test-instance-notification");
    // Construct operator tree
    QueryId queryId = new QueryId("stub_query");
    FragmentInstanceId instanceId =
        new FragmentInstanceId(new PlanFragmentId(queryId, 0), "stub-instance");
    FragmentInstanceStateMachine stateMachine =
        new FragmentInstanceStateMachine(instanceId, instanceNotificationExecutor);
    FragmentInstanceContext fragmentInstanceContext =
        createFragmentInstanceContext(instanceId, stateMachine);
    DriverContext driverContext = new DriverContext(fragmentInstanceContext, 0);
    PlanNodeId planNodeId1 = new PlanNodeId("1");
    driverContext.addOperatorContext(1, planNodeId1, SeriesScanOperator.class.getSimpleName());
    PlanNodeId planNodeId2 = new PlanNodeId("2");
    driverContext.addOperatorContext(2, planNodeId2, SeriesScanOperator.class.getSimpleName());
    PlanNodeId planNodeId3 = new PlanNodeId("3");
    driverContext.addOperatorContext(3, planNodeId3, SeriesScanOperator.class.getSimpleName());
    PlanNodeId planNodeId4 = new PlanNodeId("4");
    driverContext.addOperatorContext(4, planNodeId4, SeriesScanOperator.class.getSimpleName());
    PlanNodeId planNodeId5 = new PlanNodeId("5");
    driverContext.addOperatorContext(5, planNodeId5, SeriesScanOperator.class.getSimpleName());
    PlanNodeId planNodeId6 = new PlanNodeId("6");
    driverContext.addOperatorContext(6, planNodeId6, SeriesScanOperator.class.getSimpleName());
    PlanNodeId planNodeId7 = new PlanNodeId("7");
    driverContext.addOperatorContext(7, planNodeId7, SeriesScanOperator.class.getSimpleName());

    driverContext.addOperatorContext(
        8, new PlanNodeId("8"), FullOuterTimeJoinOperator.class.getSimpleName());
    driverContext.addOperatorContext(
        9, new PlanNodeId("9"), FullOuterTimeJoinOperator.class.getSimpleName());
    driverContext.addOperatorContext(
        10, new PlanNodeId("10"), FullOuterTimeJoinOperator.class.getSimpleName());
    driverContext.addOperatorContext(
        11, new PlanNodeId("11"), DeviceViewOperator.class.getSimpleName());
    driverContext.addOperatorContext(
        12, new PlanNodeId("12"), DeviceViewOperator.class.getSimpleName());
    driverContext.addOperatorContext(
        13, new PlanNodeId("13"), TreeTopKOperator.class.getSimpleName());

    NonAlignedFullPath measurementPath1 =
        new NonAlignedFullPath(
            IDeviceID.Factory.DEFAULT_FACTORY.create(TOP_K_OPERATOR_TEST_SG + ".device0"),
            new MeasurementSchema("sensor0", TSDataType.INT32));
    SeriesScanOperator seriesScanOperator1 =
        new SeriesScanOperator(
            driverContext.getOperatorContexts().get(0),
            planNodeId1,
            measurementPath1,
            timeOrdering,
            SeriesScanOptions.getDefaultSeriesScanOptions(measurementPath1));
    seriesScanOperator1.initQueryDataSource(new QueryDataSource(seqResources, unSeqResources));
    OperatorContext.setMaxRunTime(new Duration(500, TimeUnit.MILLISECONDS));

    NonAlignedFullPath measurementPath2 =
        new NonAlignedFullPath(
            IDeviceID.Factory.DEFAULT_FACTORY.create(TOP_K_OPERATOR_TEST_SG + ".device1"),
            new MeasurementSchema("sensor0", TSDataType.INT32));
    SeriesScanOperator seriesScanOperator2 =
        new SeriesScanOperator(
            driverContext.getOperatorContexts().get(1),
            planNodeId2,
            measurementPath2,
            timeOrdering,
            SeriesScanOptions.getDefaultSeriesScanOptions(measurementPath2));
    seriesScanOperator2.initQueryDataSource(new QueryDataSource(seqResources, unSeqResources));
    OperatorContext.setMaxRunTime(new Duration(500, TimeUnit.MILLISECONDS));

    NonAlignedFullPath measurementPath3 =
        new NonAlignedFullPath(
            IDeviceID.Factory.DEFAULT_FACTORY.create(TOP_K_OPERATOR_TEST_SG + ".device1"),
            new MeasurementSchema("sensor1", TSDataType.INT32));
    SeriesScanOperator seriesScanOperator3 =
        new SeriesScanOperator(
            driverContext.getOperatorContexts().get(2),
            planNodeId3,
            measurementPath3,
            timeOrdering,
            SeriesScanOptions.getDefaultSeriesScanOptions(measurementPath3));
    seriesScanOperator3.initQueryDataSource(new QueryDataSource(seqResources, unSeqResources));
    OperatorContext.setMaxRunTime(new Duration(500, TimeUnit.MILLISECONDS));

    NonAlignedFullPath measurementPath4 =
        new NonAlignedFullPath(
            IDeviceID.Factory.DEFAULT_FACTORY.create(TOP_K_OPERATOR_TEST_SG + ".device2"),
            new MeasurementSchema("sensor0", TSDataType.INT32));
    SeriesScanOperator seriesScanOperator4 =
        new SeriesScanOperator(
            driverContext.getOperatorContexts().get(3),
            planNodeId4,
            measurementPath4,
            timeOrdering,
            SeriesScanOptions.getDefaultSeriesScanOptions(measurementPath4));
    seriesScanOperator4.initQueryDataSource(new QueryDataSource(seqResources, unSeqResources));
    OperatorContext.setMaxRunTime(new Duration(500, TimeUnit.MILLISECONDS));

    NonAlignedFullPath measurementPath5 =
        new NonAlignedFullPath(
            IDeviceID.Factory.DEFAULT_FACTORY.create(TOP_K_OPERATOR_TEST_SG + ".device2"),
            new MeasurementSchema("sensor1", TSDataType.INT32));
    SeriesScanOperator seriesScanOperator5 =
        new SeriesScanOperator(
            driverContext.getOperatorContexts().get(4),
            planNodeId5,
            measurementPath5,
            timeOrdering,
            SeriesScanOptions.getDefaultSeriesScanOptions(measurementPath5));
    seriesScanOperator5.initQueryDataSource(new QueryDataSource(seqResources, unSeqResources));
    OperatorContext.setMaxRunTime(new Duration(500, TimeUnit.MILLISECONDS));

    NonAlignedFullPath measurementPath6 =
        new NonAlignedFullPath(
            IDeviceID.Factory.DEFAULT_FACTORY.create(TOP_K_OPERATOR_TEST_SG + ".device3"),
            new MeasurementSchema("sensor0", TSDataType.INT32));
    SeriesScanOperator seriesScanOperator6 =
        new SeriesScanOperator(
            driverContext.getOperatorContexts().get(5),
            planNodeId6,
            measurementPath6,
            timeOrdering,
            SeriesScanOptions.getDefaultSeriesScanOptions(measurementPath6));
    seriesScanOperator6.initQueryDataSource(new QueryDataSource(seqResources, unSeqResources));
    OperatorContext.setMaxRunTime(new Duration(500, TimeUnit.MILLISECONDS));

    NonAlignedFullPath measurementPath7 =
        new NonAlignedFullPath(
            IDeviceID.Factory.DEFAULT_FACTORY.create(TOP_K_OPERATOR_TEST_SG + ".device3"),
            new MeasurementSchema("sensor1", TSDataType.INT32));
    SeriesScanOperator seriesScanOperator7 =
        new SeriesScanOperator(
            driverContext.getOperatorContexts().get(6),
            planNodeId7,
            measurementPath7,
            timeOrdering,
            SeriesScanOptions.getDefaultSeriesScanOptions(measurementPath7));
    seriesScanOperator7.initQueryDataSource(new QueryDataSource(seqResources, unSeqResources));
    OperatorContext.setMaxRunTime(new Duration(500, TimeUnit.MILLISECONDS));

    List<TSDataType> tsDataTypes =
        new LinkedList<>(Arrays.asList(TSDataType.TEXT, TSDataType.INT32, TSDataType.INT32));
    FullOuterTimeJoinOperator timeJoinOperator1 =
        new FullOuterTimeJoinOperator(
            driverContext.getOperatorContexts().get(7),
            Arrays.asList(seriesScanOperator2, seriesScanOperator3),
            timeOrdering,
            Arrays.asList(TSDataType.INT32, TSDataType.INT32),
            Arrays.asList(
                new SingleColumnMerger(
                    new InputLocation(0, 0),
                    timeOrdering == Ordering.ASC
                        ? new AscTimeComparator()
                        : new DescTimeComparator()),
                new SingleColumnMerger(
                    new InputLocation(1, 0),
                    timeOrdering == Ordering.ASC
                        ? new AscTimeComparator()
                        : new DescTimeComparator())),
            timeOrdering == Ordering.ASC ? new AscTimeComparator() : new DescTimeComparator());
    OperatorContext.setMaxRunTime(new Duration(500, TimeUnit.MILLISECONDS));
    FullOuterTimeJoinOperator timeJoinOperator2 =
        new FullOuterTimeJoinOperator(
            driverContext.getOperatorContexts().get(8),
            Arrays.asList(seriesScanOperator4, seriesScanOperator5),
            timeOrdering,
            Arrays.asList(TSDataType.INT32, TSDataType.INT32),
            Arrays.asList(
                new SingleColumnMerger(
                    new InputLocation(0, 0),
                    timeOrdering == Ordering.ASC
                        ? new AscTimeComparator()
                        : new DescTimeComparator()),
                new SingleColumnMerger(
                    new InputLocation(1, 0),
                    timeOrdering == Ordering.ASC
                        ? new AscTimeComparator()
                        : new DescTimeComparator())),
            timeOrdering == Ordering.ASC ? new AscTimeComparator() : new DescTimeComparator());
    OperatorContext.setMaxRunTime(new Duration(500, TimeUnit.MILLISECONDS));
    FullOuterTimeJoinOperator timeJoinOperator3 =
        new FullOuterTimeJoinOperator(
            driverContext.getOperatorContexts().get(9),
            Arrays.asList(seriesScanOperator6, seriesScanOperator7),
            timeOrdering,
            Arrays.asList(TSDataType.INT32, TSDataType.INT32),
            Arrays.asList(
                new SingleColumnMerger(
                    new InputLocation(0, 0),
                    timeOrdering == Ordering.ASC
                        ? new AscTimeComparator()
                        : new DescTimeComparator()),
                new SingleColumnMerger(
                    new InputLocation(1, 0),
                    timeOrdering == Ordering.ASC
                        ? new AscTimeComparator()
                        : new DescTimeComparator())),
            timeOrdering == Ordering.ASC ? new AscTimeComparator() : new DescTimeComparator());
    OperatorContext.setMaxRunTime(new Duration(500, TimeUnit.MILLISECONDS));
    List<String> devices = new ArrayList<>(Arrays.asList(DEVICE0, DEVICE1, DEVICE2, DEVICE3));
    if (deviceOrdering == Ordering.DESC) {
      Collections.reverse(devices);
    }
    List<List<Integer>> deviceColumnIndex =
        Arrays.asList(Collections.singletonList(1), Arrays.asList(1, 2));
    if (deviceOrdering == Ordering.DESC) {
      Collections.reverse(deviceColumnIndex);
    }
    DeviceViewOperator deviceViewOperator1 =
        new DeviceViewOperator(
            driverContext.getOperatorContexts().get(10),
            deviceOrdering == Ordering.ASC
                ? Arrays.asList(DEVICE0_ID, DEVICE1_ID)
                : Arrays.asList(DEVICE1_ID, DEVICE0_ID),
            deviceOrdering == Ordering.ASC
                ? Arrays.asList(seriesScanOperator1, timeJoinOperator1)
                : Arrays.asList(timeJoinOperator1, seriesScanOperator1),
            deviceColumnIndex,
            tsDataTypes);
    deviceColumnIndex = Arrays.asList(Arrays.asList(1, 2), Arrays.asList(1, 2));
    DeviceViewOperator deviceViewOperator2 =
        new DeviceViewOperator(
            driverContext.getOperatorContexts().get(11),
            deviceOrdering == Ordering.ASC
                ? Arrays.asList(DEVICE2_ID, DEVICE3_ID)
                : Arrays.asList(DEVICE3_ID, DEVICE2_ID),
            deviceOrdering == Ordering.ASC
                ? Arrays.asList(timeJoinOperator2, timeJoinOperator3)
                : Arrays.asList(timeJoinOperator3, timeJoinOperator2),
            deviceColumnIndex,
            tsDataTypes);
    TreeTopKOperator topKOperator =
        new TreeTopKOperator(
            driverContext.getOperatorContexts().get(12),
            Arrays.asList(deviceViewOperator1, deviceViewOperator2),
            tsDataTypes,
            MergeSortComparator.getComparator(
                Arrays.asList(
                    new SortItem(OrderByKey.DEVICE, deviceOrdering),
                    new SortItem(OrderByKey.TIME, timeOrdering)),
                Arrays.asList(0, -1),
                Arrays.asList(TSDataType.TEXT, TSDataType.INT64)),
            limitValue,
            false);
    OperatorContext.setMaxRunTime(new Duration(500, TimeUnit.MILLISECONDS));
    return topKOperator;
  }
The original data and structure of this test is same as {@link MergeTreeSortOperatorTest}.
iotdb-core/datanode/src/test/java/org/apache/iotdb/db/queryengine/execution/operator/TreeTopKOperatorTest.java