be/src/exprs/aggregate/aggregate_function_distinct.cpp
Line | Count | Source |
1 | | // Licensed to the Apache Software Foundation (ASF) under one |
2 | | // or more contributor license agreements. See the NOTICE file |
3 | | // distributed with this work for additional information |
4 | | // regarding copyright ownership. The ASF licenses this file |
5 | | // to you under the Apache License, Version 2.0 (the |
6 | | // "License"); you may not use this file except in compliance |
7 | | // with the License. You may obtain a copy of the License at |
8 | | // |
9 | | // http://www.apache.org/licenses/LICENSE-2.0 |
10 | | // |
11 | | // Unless required by applicable law or agreed to in writing, |
12 | | // software distributed under the License is distributed on an |
13 | | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY |
14 | | // KIND, either express or implied. See the License for the |
15 | | // specific language governing permissions and limitations |
16 | | // under the License. |
17 | | // This file is copied from |
18 | | // https://github.com/ClickHouse/ClickHouse/blob/master/src/AggregateFunctions/AggregateFunctionDistinct.cpp |
19 | | // and modified by Doris |
20 | | |
21 | | #include "exprs/aggregate/aggregate_function_distinct.h" |
22 | | |
23 | | #include <algorithm> |
24 | | |
25 | | #include "core/data_type/data_type_nullable.h" |
26 | | #include "exprs/aggregate/aggregate_function_combinator.h" |
27 | | #include "exprs/aggregate/aggregate_function_simple_factory.h" |
28 | | #include "exprs/aggregate/helpers.h" |
29 | | |
30 | | namespace doris { |
31 | | |
32 | | template <PrimitiveType T> |
33 | | struct Reducer { |
34 | | template <bool stable> |
35 | | using Output = AggregateFunctionDistinctSingleNumericData<T, stable>; |
36 | | using AggregateFunctionDistinctNormal = AggregateFunctionDistinct<Output, false>; |
37 | | }; |
38 | | |
39 | | template <PrimitiveType T> |
40 | | using AggregateFunctionDistinctNumeric = typename Reducer<T>::AggregateFunctionDistinctNormal; |
41 | | |
42 | | class AggregateFunctionCombinatorDistinct final : public IAggregateFunctionCombinator { |
43 | | public: |
44 | 0 | String get_name() const override { return "Distinct"; } |
45 | | |
46 | 1.96k | DataTypes transform_arguments(const DataTypes& arguments) const override { |
47 | 1.96k | if (arguments.empty()) { |
48 | 0 | throw doris::Exception( |
49 | 0 | ErrorCode::INTERNAL_ERROR, |
50 | 0 | "Incorrect number of arguments for aggregate function with Distinct suffix"); |
51 | 0 | } |
52 | 1.96k | return arguments; |
53 | 1.96k | } |
54 | | |
55 | | AggregateFunctionPtr transform_aggregate_function( |
56 | | const AggregateFunctionPtr& nested_function, const DataTypes& arguments, |
57 | 1.96k | const bool result_is_nullable, const AggregateFunctionAttr& attr) const override { |
58 | 1.96k | DCHECK(nested_function != nullptr); |
59 | 1.96k | if (nested_function == nullptr) { |
60 | 0 | return nullptr; |
61 | 0 | } |
62 | | |
63 | 1.96k | if (arguments.size() == 1) { |
64 | 1.93k | AggregateFunctionPtr res( |
65 | 1.93k | creator_with_type_list<TYPE_TINYINT, TYPE_SMALLINT, TYPE_INT, TYPE_BIGINT, |
66 | 1.93k | TYPE_LARGEINT>:: |
67 | 1.93k | create<AggregateFunctionDistinctNumeric>(arguments, result_is_nullable, |
68 | 1.93k | attr, nested_function)); |
69 | 1.93k | if (res) { |
70 | 1.11k | return res; |
71 | 1.11k | } |
72 | | |
73 | 818 | res = creator_without_type::create< |
74 | 818 | AggregateFunctionDistinct<AggregateFunctionDistinctSingleGenericData>>( |
75 | 818 | arguments, result_is_nullable, attr, nested_function); |
76 | 818 | return res; |
77 | 1.93k | } |
78 | 25 | return creator_without_type::create< |
79 | 25 | AggregateFunctionDistinct<AggregateFunctionDistinctMultipleGenericData>>( |
80 | 25 | arguments, result_is_nullable, attr, nested_function); |
81 | 1.96k | } |
82 | | }; |
83 | | |
84 | 6 | void register_aggregate_function_combinator_distinct(AggregateFunctionSimpleFactory& factory) { |
85 | 6 | AggregateFunctionCreator creator = [&](const std::string& name, const DataTypes& types, |
86 | 6 | const DataTypePtr& result_type, |
87 | 6 | const bool result_is_nullable, |
88 | 1.95k | const AggregateFunctionAttr& attr) { |
89 | | // 1. we should get not nullable types; |
90 | 1.95k | DataTypes nested_types(types.size()); |
91 | 1.95k | std::ranges::transform(types, nested_types.begin(), |
92 | 1.98k | [](const auto& e) { return remove_nullable(e); }); |
93 | 1.95k | auto function_combinator = std::make_shared<AggregateFunctionCombinatorDistinct>(); |
94 | 1.95k | auto transform_arguments = function_combinator->transform_arguments(nested_types); |
95 | 1.95k | auto nested_function_name = name.substr(DISTINCT_FUNCTION_PREFIX.size()); |
96 | 1.95k | auto nested_function = factory.get(nested_function_name, transform_arguments, result_type, |
97 | 1.95k | false, BeExecVersionManager::get_newest_version(), attr); |
98 | 1.95k | return function_combinator->transform_aggregate_function(nested_function, types, |
99 | 1.95k | result_is_nullable, attr); |
100 | 1.95k | }; |
101 | 6 | factory.register_distinct_function_combinator(creator, DISTINCT_FUNCTION_PREFIX); |
102 | 6 | factory.register_distinct_function_combinator(creator, DISTINCT_FUNCTION_PREFIX, true); |
103 | 6 | } |
104 | | } // namespace doris |