Coverage Report

Created: 2026-07-17 11:15

next uncovered line (L), next uncovered region (R), next uncovered branch (B)
be/src/exprs/function/function_bitmap.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/Functions/FunctionBitmap.h
19
// and modified by Doris
20
21
#include <absl/strings/numbers.h>
22
#include <absl/strings/str_split.h>
23
#include <glog/logging.h>
24
#include <stdint.h>
25
#include <string.h>
26
27
#include <algorithm>
28
#include <boost/iterator/iterator_facade.hpp>
29
#include <functional>
30
#include <memory>
31
#include <ostream>
32
#include <string>
33
#include <utility>
34
#include <vector>
35
36
#include "common/compiler_util.h" // IWYU pragma: keep
37
#include "common/status.h"
38
#include "core/assert_cast.h"
39
#include "core/block/block.h"
40
#include "core/block/column_numbers.h"
41
#include "core/block/column_with_type_and_name.h"
42
#include "core/column/column.h"
43
#include "core/column/column_array.h"
44
#include "core/column/column_complex.h"
45
#include "core/column/column_const.h"
46
#include "core/column/column_nullable.h"
47
#include "core/column/column_string.h"
48
#include "core/column/column_vector.h"
49
#include "core/data_type/data_type.h"
50
#include "core/data_type/data_type_array.h"
51
#include "core/data_type/data_type_bitmap.h"
52
#include "core/data_type/data_type_nullable.h"
53
#include "core/data_type/data_type_number.h"
54
#include "core/data_type/data_type_string.h"
55
#include "core/field.h"
56
#include "core/types.h"
57
#include "core/value/bitmap_value.h"
58
#include "exec/common/stringop_substring.h"
59
#include "exec/common/util.hpp"
60
#include "exprs/aggregate/aggregate_function.h"
61
#include "exprs/function/function.h"
62
#include "exprs/function/function_always_not_nullable.h"
63
#include "exprs/function/function_bitmap_min_or_max.h"
64
#include "exprs/function/function_const.h"
65
#include "exprs/function/function_helpers.h"
66
#include "exprs/function/function_totype.h"
67
#include "exprs/function/simple_function_factory.h"
68
#include "util/hash/murmur_hash3.h"
69
#include "util/hash_util.hpp"
70
#include "util/string_parser.hpp"
71
#include "util/url_coding.h"
72
73
namespace doris {
74
class FunctionContext;
75
} // namespace doris
76
77
namespace doris {
78
79
struct BitmapEmpty {
80
    static constexpr auto name = "bitmap_empty";
81
    using ReturnColVec = ColumnBitmap;
82
0
    static DataTypePtr get_return_type() { return std::make_shared<DataTypeBitMap>(); }
83
0
    static auto init_value() { return BitmapValue {}; }
84
};
85
86
struct ToBitmap {
87
    static constexpr auto name = "to_bitmap";
88
    using ReturnType = DataTypeBitMap;
89
90
    template <typename ColumnType>
91
0
    static void vector(const ColumnType* col, MutableColumnPtr& col_res) {
92
0
        execute<ColumnType, false>(col, nullptr, col_res);
93
0
    }
Unexecuted instantiation: _ZN5doris8ToBitmap6vectorINS_9ColumnStrIjEEEEvPKT_RNS_3COWINS_7IColumnEE11mutable_ptrIS8_EE
Unexecuted instantiation: _ZN5doris8ToBitmap6vectorINS_12ColumnVectorILNS_13PrimitiveTypeE6EEEEEvPKT_RNS_3COWINS_7IColumnEE11mutable_ptrIS9_EE
94
    template <typename ColumnType>
95
    static void vector_nullable(const ColumnType* col, const NullMap& nullmap,
96
0
                                MutableColumnPtr& col_res) {
97
0
        execute<ColumnType, true>(col, &nullmap, col_res);
98
0
    }
Unexecuted instantiation: _ZN5doris8ToBitmap15vector_nullableINS_9ColumnStrIjEEEEvPKT_RKNS_8PODArrayIhLm4096ENS_9AllocatorILb0ELb0ELb0ENS_22DefaultMemoryAllocatorELb1EEELm16ELm15EEERNS_3COWINS_7IColumnEE11mutable_ptrISF_EE
Unexecuted instantiation: _ZN5doris8ToBitmap15vector_nullableINS_12ColumnVectorILNS_13PrimitiveTypeE6EEEEEvPKT_RKNS_8PODArrayIhLm4096ENS_9AllocatorILb0ELb0ELb0ENS_22DefaultMemoryAllocatorELb1EEELm16ELm15EEERNS_3COWINS_7IColumnEE11mutable_ptrISG_EE
99
    template <typename ColumnType, bool arg_is_nullable>
100
0
    static void execute(const ColumnType* col, const NullMap* nullmap, MutableColumnPtr& col_res) {
101
0
        if constexpr (std::is_same_v<ColumnType, ColumnString>) {
102
0
            const ColumnString::Chars& data = col->get_chars();
103
0
            const ColumnString::Offsets& offsets = col->get_offsets();
104
105
0
            auto* res_column = reinterpret_cast<ColumnBitmap*>(col_res.get());
106
0
            auto& res_data = res_column->get_data();
107
0
            size_t size = offsets.size();
108
109
0
            for (size_t i = 0; i < size; ++i) {
110
0
                if (arg_is_nullable && ((*nullmap)[i])) {
111
0
                    continue;
112
0
                } else {
113
0
                    const char* raw_str = reinterpret_cast<const char*>(&data[offsets[i - 1]]);
114
0
                    int str_size = cast_set<int>(offsets[i] - offsets[i - 1]);
115
0
                    StringParser::ParseResult parse_result = StringParser::PARSE_SUCCESS;
116
0
                    uint64_t int_value = StringParser::string_to_unsigned_int<uint64_t>(
117
0
                            raw_str, str_size, &parse_result);
118
0
                    if (LIKELY(parse_result == StringParser::PARSE_SUCCESS)) {
119
0
                        res_data[i].add(int_value);
120
0
                    }
121
0
                }
122
0
            }
123
0
        } else if constexpr (std::is_same_v<ColumnType, ColumnInt64>) {
124
0
            auto* res_column = reinterpret_cast<ColumnBitmap*>(col_res.get());
125
0
            auto& res_data = res_column->get_data();
126
0
            size_t size = col->size();
127
128
0
            for (size_t i = 0; i < size; ++i) {
129
0
                if constexpr (arg_is_nullable) {
130
0
                    if ((*nullmap)[i]) {
131
0
                        continue;
132
0
                    }
133
0
                }
134
0
                if (auto value = col->get_data()[i]; value >= 0) {
135
0
                    res_data[i].add(value);
136
0
                }
137
0
            }
138
0
        }
139
0
    }
Unexecuted instantiation: _ZN5doris8ToBitmap7executeINS_9ColumnStrIjEELb1EEEvPKT_PKNS_8PODArrayIhLm4096ENS_9AllocatorILb0ELb0ELb0ENS_22DefaultMemoryAllocatorELb1EEELm16ELm15EEERNS_3COWINS_7IColumnEE11mutable_ptrISF_EE
Unexecuted instantiation: _ZN5doris8ToBitmap7executeINS_12ColumnVectorILNS_13PrimitiveTypeE6EEELb1EEEvPKT_PKNS_8PODArrayIhLm4096ENS_9AllocatorILb0ELb0ELb0ENS_22DefaultMemoryAllocatorELb1EEELm16ELm15EEERNS_3COWINS_7IColumnEE11mutable_ptrISG_EE
Unexecuted instantiation: _ZN5doris8ToBitmap7executeINS_9ColumnStrIjEELb0EEEvPKT_PKNS_8PODArrayIhLm4096ENS_9AllocatorILb0ELb0ELb0ENS_22DefaultMemoryAllocatorELb1EEELm16ELm15EEERNS_3COWINS_7IColumnEE11mutable_ptrISF_EE
Unexecuted instantiation: _ZN5doris8ToBitmap7executeINS_12ColumnVectorILNS_13PrimitiveTypeE6EEELb0EEEvPKT_PKNS_8PODArrayIhLm4096ENS_9AllocatorILb0ELb0ELb0ENS_22DefaultMemoryAllocatorELb1EEELm16ELm15EEERNS_3COWINS_7IColumnEE11mutable_ptrISG_EE
140
};
141
142
struct ToBitmapWithCheck {
143
    static constexpr auto name = "to_bitmap_with_check";
144
    using ReturnType = DataTypeBitMap;
145
146
    template <typename ColumnType>
147
0
    static Status vector(const ColumnType* col, MutableColumnPtr& col_res) {
148
0
        return execute<ColumnType, false>(col, nullptr, col_res);
149
0
    }
Unexecuted instantiation: _ZN5doris17ToBitmapWithCheck6vectorINS_9ColumnStrIjEEEENS_6StatusEPKT_RNS_3COWINS_7IColumnEE11mutable_ptrIS9_EE
Unexecuted instantiation: _ZN5doris17ToBitmapWithCheck6vectorINS_12ColumnVectorILNS_13PrimitiveTypeE6EEEEENS_6StatusEPKT_RNS_3COWINS_7IColumnEE11mutable_ptrISA_EE
150
    template <typename ColumnType>
151
    static Status vector_nullable(const ColumnType* col, const NullMap& nullmap,
152
0
                                  MutableColumnPtr& col_res) {
153
0
        return execute<ColumnType, true>(col, &nullmap, col_res);
154
0
    }
Unexecuted instantiation: _ZN5doris17ToBitmapWithCheck15vector_nullableINS_9ColumnStrIjEEEENS_6StatusEPKT_RKNS_8PODArrayIhLm4096ENS_9AllocatorILb0ELb0ELb0ENS_22DefaultMemoryAllocatorELb1EEELm16ELm15EEERNS_3COWINS_7IColumnEE11mutable_ptrISG_EE
Unexecuted instantiation: _ZN5doris17ToBitmapWithCheck15vector_nullableINS_12ColumnVectorILNS_13PrimitiveTypeE6EEEEENS_6StatusEPKT_RKNS_8PODArrayIhLm4096ENS_9AllocatorILb0ELb0ELb0ENS_22DefaultMemoryAllocatorELb1EEELm16ELm15EEERNS_3COWINS_7IColumnEE11mutable_ptrISH_EE
155
    template <typename ColumnType, bool arg_is_nullable>
156
    static Status execute(const ColumnType* col, const NullMap* nullmap,
157
0
                          MutableColumnPtr& col_res) {
158
0
        if constexpr (std::is_same_v<ColumnType, ColumnString>) {
159
0
            const ColumnString::Chars& data = col->get_chars();
160
0
            const ColumnString::Offsets& offsets = col->get_offsets();
161
0
            auto* res_column = reinterpret_cast<ColumnBitmap*>(col_res.get());
162
0
            auto& res_data = res_column->get_data();
163
0
            size_t size = offsets.size();
164
165
0
            for (size_t i = 0; i < size; ++i) {
166
0
                if (arg_is_nullable && ((*nullmap)[i])) {
167
0
                    continue;
168
0
                } else {
169
0
                    const char* raw_str = reinterpret_cast<const char*>(&data[offsets[i - 1]]);
170
                    // The string lenght is less than 2G, so that cast the str size to int, not use size_t
171
0
                    int str_size = cast_set<int>(offsets[i] - offsets[i - 1]);
172
0
                    StringParser::ParseResult parse_result = StringParser::PARSE_SUCCESS;
173
0
                    uint64_t int_value = StringParser::string_to_unsigned_int<uint64_t>(
174
0
                            raw_str, str_size, &parse_result);
175
0
                    if (LIKELY(parse_result == StringParser::PARSE_SUCCESS)) {
176
0
                        res_data[i].add(int_value);
177
0
                    } else {
178
0
                        return Status::InvalidArgument(
179
0
                                "The input: {} is not valid, to_bitmap only support bigint value "
180
0
                                "from 0 to 18446744073709551615 currently, cannot create MV with "
181
0
                                "to_bitmap on column with negative values or cannot load negative "
182
0
                                "values to column with to_bitmap MV on it.",
183
0
                                std::string(raw_str, str_size));
184
0
                    }
185
0
                }
186
0
            }
187
0
        } else if constexpr (std::is_same_v<ColumnType, ColumnInt64>) {
188
0
            auto* res_column = reinterpret_cast<ColumnBitmap*>(col_res.get());
189
0
            auto& res_data = res_column->get_data();
190
0
            size_t size = col->size();
191
192
0
            for (size_t i = 0; i < size; ++i) {
193
0
                if (arg_is_nullable && ((*nullmap)[i])) {
194
0
                    continue;
195
0
                } else {
196
0
                    int64_t int_value = col->get_data()[i];
197
0
                    if (LIKELY(int_value >= 0)) {
198
0
                        res_data[i].add(int_value);
199
0
                    } else {
200
0
                        return Status::InvalidArgument(
201
0
                                "The input: {} is not valid, to_bitmap only support bigint value "
202
0
                                "from 0 to 18446744073709551615 currently, cannot create MV with "
203
0
                                "to_bitmap on column with negative values or cannot load negative "
204
0
                                "values to column with to_bitmap MV on it.",
205
0
                                int_value);
206
0
                    }
207
0
                }
208
0
            }
209
        } else {
210
            return Status::InvalidArgument("not support type");
211
        }
212
0
        return Status::OK();
213
0
    }
Unexecuted instantiation: _ZN5doris17ToBitmapWithCheck7executeINS_9ColumnStrIjEELb1EEENS_6StatusEPKT_PKNS_8PODArrayIhLm4096ENS_9AllocatorILb0ELb0ELb0ENS_22DefaultMemoryAllocatorELb1EEELm16ELm15EEERNS_3COWINS_7IColumnEE11mutable_ptrISG_EE
Unexecuted instantiation: _ZN5doris17ToBitmapWithCheck7executeINS_12ColumnVectorILNS_13PrimitiveTypeE6EEELb1EEENS_6StatusEPKT_PKNS_8PODArrayIhLm4096ENS_9AllocatorILb0ELb0ELb0ENS_22DefaultMemoryAllocatorELb1EEELm16ELm15EEERNS_3COWINS_7IColumnEE11mutable_ptrISH_EE
Unexecuted instantiation: _ZN5doris17ToBitmapWithCheck7executeINS_9ColumnStrIjEELb0EEENS_6StatusEPKT_PKNS_8PODArrayIhLm4096ENS_9AllocatorILb0ELb0ELb0ENS_22DefaultMemoryAllocatorELb1EEELm16ELm15EEERNS_3COWINS_7IColumnEE11mutable_ptrISG_EE
Unexecuted instantiation: _ZN5doris17ToBitmapWithCheck7executeINS_12ColumnVectorILNS_13PrimitiveTypeE6EEELb0EEENS_6StatusEPKT_PKNS_8PODArrayIhLm4096ENS_9AllocatorILb0ELb0ELb0ENS_22DefaultMemoryAllocatorELb1EEELm16ELm15EEERNS_3COWINS_7IColumnEE11mutable_ptrISH_EE
214
};
215
216
struct BitmapFromString {
217
    using ArgumentType = DataTypeString;
218
219
    static constexpr auto name = "bitmap_from_string";
220
221
    static Status vector(const ColumnString::Chars& data, const ColumnString::Offsets& offsets,
222
                         std::vector<BitmapValue>& res, NullMap& null_map,
223
2
                         size_t input_rows_count) {
224
2
        res.reserve(input_rows_count);
225
2
        std::vector<uint64_t> bits;
226
2
        if (offsets.size() == 0 && input_rows_count == 1) {
227
            // For NULL constant
228
0
            res.emplace_back();
229
0
            null_map[0] = 1;
230
0
            return Status::OK();
231
0
        }
232
233
16
        auto split_and_parse = [&bits](const char* raw_str, size_t str_size) {
234
16
            bits.clear();
235
16
            auto res = absl::StrSplit(std::string_view {raw_str, str_size}, ",", absl::SkipEmpty());
236
16
            uint64_t value = 0;
237
38
            for (auto s : res) {
238
38
                if (!absl::SimpleAtoi(s, &value)) {
239
3
                    return false;
240
3
                }
241
35
                bits.push_back(value);
242
35
            }
243
13
            return true;
244
16
        };
245
246
        // split by comma
247
248
18
        for (size_t i = 0; i < input_rows_count; ++i) {
249
16
            const char* raw_str = reinterpret_cast<const char*>(&data[offsets[i - 1]]);
250
16
            int64_t str_size = offsets[i] - offsets[i - 1];
251
252
16
            if ((str_size > INT32_MAX) || !split_and_parse(raw_str, str_size)) {
253
3
                res.emplace_back();
254
3
                null_map[i] = 1;
255
3
                continue;
256
3
            }
257
13
            res.emplace_back(bits);
258
13
        }
259
2
        return Status::OK();
260
2
    }
261
};
262
263
struct NameBitmapFromBase64 {
264
    static constexpr auto name = "bitmap_from_base64";
265
};
266
struct BitmapFromBase64 {
267
    using ArgumentType = DataTypeString;
268
269
    static constexpr auto name = "bitmap_from_base64";
270
271
    static Status vector(const ColumnString::Chars& data, const ColumnString::Offsets& offsets,
272
                         std::vector<BitmapValue>& res, NullMap& null_map,
273
6
                         size_t input_rows_count) {
274
6
        res.reserve(input_rows_count);
275
6
        if (offsets.size() == 0 && input_rows_count == 1) {
276
            // For NULL constant
277
0
            res.emplace_back();
278
0
            null_map[0] = 1;
279
0
            return Status::OK();
280
0
        }
281
6
        std::string decode_buff;
282
6
        size_t last_decode_buff_len = 0;
283
6
        size_t curr_decode_buff_len = 0;
284
29
        for (size_t i = 0; i < input_rows_count; ++i) {
285
23
            const char* src_str = reinterpret_cast<const char*>(&data[offsets[i - 1]]);
286
23
            size_t src_size = offsets[i] - offsets[i - 1];
287
23
            if (0 != src_size % 4) {
288
                // return Status::InvalidArgument(
289
                //         fmt::format("invalid base64: {}", std::string(src_str, src_size)));
290
0
                res.emplace_back();
291
0
                null_map[i] = 1;
292
0
                continue;
293
0
            }
294
23
            curr_decode_buff_len = src_size + 3;
295
23
            if (curr_decode_buff_len > last_decode_buff_len) {
296
13
                decode_buff.resize(curr_decode_buff_len);
297
13
                last_decode_buff_len = curr_decode_buff_len;
298
13
            }
299
23
            auto outlen = base64_decode(src_str, src_size, decode_buff.data());
300
23
            if (outlen < 0) {
301
0
                res.emplace_back();
302
0
                null_map[i] = 1;
303
23
            } else {
304
23
                BitmapValue bitmap_val;
305
23
                if (!bitmap_val.deserialize(decode_buff.data())) {
306
0
                    return Status::RuntimeError("bitmap_from_base64 decode failed: base64: {}",
307
0
                                                std::string(src_str, src_size));
308
0
                }
309
23
                res.emplace_back(std::move(bitmap_val));
310
23
            }
311
23
        }
312
6
        return Status::OK();
313
6
    }
314
};
315
struct BitmapFromArray {
316
    using ArgumentType = DataTypeArray;
317
    static constexpr auto name = "bitmap_from_array";
318
319
    template <typename ColumnType>
320
    static Status vector(const ColumnArray::Offsets64& offset_column_data,
321
                         const IColumn& nested_column, const NullMap& nested_null_map,
322
0
                         std::vector<BitmapValue>& res, NullMap& null_map) {
323
0
        const auto& nested_column_data = static_cast<const ColumnType&>(nested_column).get_data();
324
0
        auto size = offset_column_data.size();
325
0
        res.reserve(size);
326
        // Preserve the nested column's native integer type here.
327
        // For Array<Int32>/Array<UInt32>-like inputs can reach the 32-bit `add_many` fast path
328
        // instead of widening every element to uint64_t first.
329
0
        using ValueType = typename ColumnType::value_type;
330
0
        std::vector<ValueType> bits;
331
0
        for (size_t i = 0; i < size; ++i) {
332
0
            auto curr_offset = offset_column_data[i];
333
0
            auto prev_offset = offset_column_data[i - 1];
334
0
            bits.reserve(curr_offset - prev_offset);
335
0
            for (auto j = prev_offset; j < curr_offset; ++j) {
336
0
                auto data = nested_column_data[j];
337
                // invaild value
338
0
                if (UNLIKELY(data < 0) || UNLIKELY(nested_null_map[j])) {
339
0
                    res.emplace_back();
340
0
                    null_map[i] = 1;
341
0
                    break;
342
0
                } else {
343
0
                    bits.push_back(data);
344
0
                }
345
0
            }
346
            //input is valid value
347
0
            if (!null_map[i]) {
348
0
                res.emplace_back(bits);
349
0
            }
350
0
            bits.clear();
351
0
        }
352
0
        return Status::OK();
353
0
    }
Unexecuted instantiation: _ZN5doris15BitmapFromArray6vectorINS_12ColumnVectorILNS_13PrimitiveTypeE3EEEEENS_6StatusERKNS_8PODArrayImLm4096ENS_9AllocatorILb0ELb0ELb0ENS_22DefaultMemoryAllocatorELb1EEELm16ELm15EEERKNS_7IColumnERKNS6_IhLm4096ES9_Lm16ELm15EEERSt6vectorINS_11BitmapValueESaISK_EERSG_
Unexecuted instantiation: _ZN5doris15BitmapFromArray6vectorINS_12ColumnVectorILNS_13PrimitiveTypeE2EEEEENS_6StatusERKNS_8PODArrayImLm4096ENS_9AllocatorILb0ELb0ELb0ENS_22DefaultMemoryAllocatorELb1EEELm16ELm15EEERKNS_7IColumnERKNS6_IhLm4096ES9_Lm16ELm15EEERSt6vectorINS_11BitmapValueESaISK_EERSG_
Unexecuted instantiation: _ZN5doris15BitmapFromArray6vectorINS_12ColumnVectorILNS_13PrimitiveTypeE4EEEEENS_6StatusERKNS_8PODArrayImLm4096ENS_9AllocatorILb0ELb0ELb0ENS_22DefaultMemoryAllocatorELb1EEELm16ELm15EEERKNS_7IColumnERKNS6_IhLm4096ES9_Lm16ELm15EEERSt6vectorINS_11BitmapValueESaISK_EERSG_
Unexecuted instantiation: _ZN5doris15BitmapFromArray6vectorINS_12ColumnVectorILNS_13PrimitiveTypeE5EEEEENS_6StatusERKNS_8PODArrayImLm4096ENS_9AllocatorILb0ELb0ELb0ENS_22DefaultMemoryAllocatorELb1EEELm16ELm15EEERKNS_7IColumnERKNS6_IhLm4096ES9_Lm16ELm15EEERSt6vectorINS_11BitmapValueESaISK_EERSG_
Unexecuted instantiation: _ZN5doris15BitmapFromArray6vectorINS_12ColumnVectorILNS_13PrimitiveTypeE6EEEEENS_6StatusERKNS_8PODArrayImLm4096ENS_9AllocatorILb0ELb0ELb0ENS_22DefaultMemoryAllocatorELb1EEELm16ELm15EEERKNS_7IColumnERKNS6_IhLm4096ES9_Lm16ELm15EEERSt6vectorINS_11BitmapValueESaISK_EERSG_
354
};
355
356
template <typename Impl>
357
class FunctionBitmapAlwaysNull : public IFunction {
358
public:
359
    static constexpr auto name = Impl::name;
360
361
3
    String get_name() const override { return name; }
_ZNK5doris24FunctionBitmapAlwaysNullINS_16BitmapFromStringEE8get_nameB5cxx11Ev
Line
Count
Source
361
1
    String get_name() const override { return name; }
_ZNK5doris24FunctionBitmapAlwaysNullINS_16BitmapFromBase64EE8get_nameB5cxx11Ev
Line
Count
Source
361
1
    String get_name() const override { return name; }
_ZNK5doris24FunctionBitmapAlwaysNullINS_15BitmapFromArrayEE8get_nameB5cxx11Ev
Line
Count
Source
361
1
    String get_name() const override { return name; }
362
363
14
    static FunctionPtr create() { return std::make_shared<FunctionBitmapAlwaysNull>(); }
_ZN5doris24FunctionBitmapAlwaysNullINS_16BitmapFromStringEE6createEv
Line
Count
Source
363
4
    static FunctionPtr create() { return std::make_shared<FunctionBitmapAlwaysNull>(); }
_ZN5doris24FunctionBitmapAlwaysNullINS_16BitmapFromBase64EE6createEv
Line
Count
Source
363
8
    static FunctionPtr create() { return std::make_shared<FunctionBitmapAlwaysNull>(); }
_ZN5doris24FunctionBitmapAlwaysNullINS_15BitmapFromArrayEE6createEv
Line
Count
Source
363
2
    static FunctionPtr create() { return std::make_shared<FunctionBitmapAlwaysNull>(); }
364
365
8
    DataTypePtr get_return_type_impl(const DataTypes& arguments) const override {
366
8
        return make_nullable(std::make_shared<DataTypeBitMap>());
367
8
    }
_ZNK5doris24FunctionBitmapAlwaysNullINS_16BitmapFromStringEE20get_return_type_implERKSt6vectorISt10shared_ptrIKNS_9IDataTypeEESaIS7_EE
Line
Count
Source
365
2
    DataTypePtr get_return_type_impl(const DataTypes& arguments) const override {
366
2
        return make_nullable(std::make_shared<DataTypeBitMap>());
367
2
    }
_ZNK5doris24FunctionBitmapAlwaysNullINS_16BitmapFromBase64EE20get_return_type_implERKSt6vectorISt10shared_ptrIKNS_9IDataTypeEESaIS7_EE
Line
Count
Source
365
6
    DataTypePtr get_return_type_impl(const DataTypes& arguments) const override {
366
6
        return make_nullable(std::make_shared<DataTypeBitMap>());
367
6
    }
Unexecuted instantiation: _ZNK5doris24FunctionBitmapAlwaysNullINS_15BitmapFromArrayEE20get_return_type_implERKSt6vectorISt10shared_ptrIKNS_9IDataTypeEESaIS7_EE
368
369
8
    size_t get_number_of_arguments() const override { return 1; }
_ZNK5doris24FunctionBitmapAlwaysNullINS_16BitmapFromStringEE23get_number_of_argumentsEv
Line
Count
Source
369
2
    size_t get_number_of_arguments() const override { return 1; }
_ZNK5doris24FunctionBitmapAlwaysNullINS_16BitmapFromBase64EE23get_number_of_argumentsEv
Line
Count
Source
369
6
    size_t get_number_of_arguments() const override { return 1; }
Unexecuted instantiation: _ZNK5doris24FunctionBitmapAlwaysNullINS_15BitmapFromArrayEE23get_number_of_argumentsEv
370
371
    Status execute_impl(FunctionContext* context, Block& block, const ColumnNumbers& arguments,
372
8
                        uint32_t result, size_t input_rows_count) const override {
373
8
        auto res_null_map = ColumnUInt8::create(input_rows_count, 0);
374
8
        auto res_data_column = ColumnBitmap::create();
375
8
        auto& null_map = res_null_map->get_data();
376
8
        auto& res = res_data_column->get_data();
377
378
8
        ColumnPtr& argument_column = block.get_by_position(arguments[0]).column;
379
8
        if constexpr (std::is_same_v<typename Impl::ArgumentType, DataTypeString>) {
380
8
            const auto& str_column = static_cast<const ColumnString&>(*argument_column);
381
8
            const ColumnString::Chars& data = str_column.get_chars();
382
8
            const ColumnString::Offsets& offsets = str_column.get_offsets();
383
8
            RETURN_IF_ERROR(Impl::vector(data, offsets, res, null_map, input_rows_count));
384
8
        } else if constexpr (std::is_same_v<typename Impl::ArgumentType, DataTypeArray>) {
385
0
            auto argument_type = remove_nullable(
386
0
                    assert_cast<const DataTypeArray&>(*block.get_by_position(arguments[0]).type)
387
0
                            .get_nested_type());
388
0
            const auto& array_column = static_cast<const ColumnArray&>(*argument_column);
389
0
            const auto& offset_column_data = array_column.get_offsets();
390
0
            const auto& nested_nullable_column =
391
0
                    static_cast<const ColumnNullable&>(array_column.get_data());
392
0
            const auto& nested_column = nested_nullable_column.get_nested_column();
393
0
            const auto& nested_null_map = nested_nullable_column.get_null_map_column().get_data();
394
395
0
            switch (argument_type->get_primitive_type()) {
396
0
            case PrimitiveType::TYPE_TINYINT:
397
0
                RETURN_IF_ERROR(Impl::template vector<ColumnInt8>(offset_column_data, nested_column,
398
0
                                                                  nested_null_map, res, null_map));
399
0
                break;
400
0
            case PrimitiveType::TYPE_BOOLEAN:
401
0
                RETURN_IF_ERROR(Impl::template vector<ColumnUInt8>(
402
0
                        offset_column_data, nested_column, nested_null_map, res, null_map));
403
0
                break;
404
0
            case PrimitiveType::TYPE_SMALLINT:
405
0
                RETURN_IF_ERROR(Impl::template vector<ColumnInt16>(
406
0
                        offset_column_data, nested_column, nested_null_map, res, null_map));
407
0
                break;
408
0
            case PrimitiveType::TYPE_INT:
409
0
                RETURN_IF_ERROR(Impl::template vector<ColumnInt32>(
410
0
                        offset_column_data, nested_column, nested_null_map, res, null_map));
411
0
                break;
412
0
            case PrimitiveType::TYPE_BIGINT:
413
0
                RETURN_IF_ERROR(Impl::template vector<ColumnInt64>(
414
0
                        offset_column_data, nested_column, nested_null_map, res, null_map));
415
0
                break;
416
0
            default:
417
0
                return Status::RuntimeError("Illegal column {} of argument of function {}",
418
0
                                            block.get_by_position(arguments[0]).column->get_name(),
419
0
                                            get_name());
420
0
            }
421
        } else {
422
            return Status::RuntimeError("Illegal column {} of argument of function {}",
423
                                        block.get_by_position(arguments[0]).column->get_name(),
424
                                        get_name());
425
        }
426
8
        block.get_by_position(result).column =
427
8
                ColumnNullable::create(std::move(res_data_column), std::move(res_null_map));
428
8
        return Status::OK();
429
8
    }
_ZNK5doris24FunctionBitmapAlwaysNullINS_16BitmapFromStringEE12execute_implEPNS_15FunctionContextERNS_5BlockERKSt6vectorIjSaIjEEjm
Line
Count
Source
372
2
                        uint32_t result, size_t input_rows_count) const override {
373
2
        auto res_null_map = ColumnUInt8::create(input_rows_count, 0);
374
2
        auto res_data_column = ColumnBitmap::create();
375
2
        auto& null_map = res_null_map->get_data();
376
2
        auto& res = res_data_column->get_data();
377
378
2
        ColumnPtr& argument_column = block.get_by_position(arguments[0]).column;
379
2
        if constexpr (std::is_same_v<typename Impl::ArgumentType, DataTypeString>) {
380
2
            const auto& str_column = static_cast<const ColumnString&>(*argument_column);
381
2
            const ColumnString::Chars& data = str_column.get_chars();
382
2
            const ColumnString::Offsets& offsets = str_column.get_offsets();
383
2
            RETURN_IF_ERROR(Impl::vector(data, offsets, res, null_map, input_rows_count));
384
        } else if constexpr (std::is_same_v<typename Impl::ArgumentType, DataTypeArray>) {
385
            auto argument_type = remove_nullable(
386
                    assert_cast<const DataTypeArray&>(*block.get_by_position(arguments[0]).type)
387
                            .get_nested_type());
388
            const auto& array_column = static_cast<const ColumnArray&>(*argument_column);
389
            const auto& offset_column_data = array_column.get_offsets();
390
            const auto& nested_nullable_column =
391
                    static_cast<const ColumnNullable&>(array_column.get_data());
392
            const auto& nested_column = nested_nullable_column.get_nested_column();
393
            const auto& nested_null_map = nested_nullable_column.get_null_map_column().get_data();
394
395
            switch (argument_type->get_primitive_type()) {
396
            case PrimitiveType::TYPE_TINYINT:
397
                RETURN_IF_ERROR(Impl::template vector<ColumnInt8>(offset_column_data, nested_column,
398
                                                                  nested_null_map, res, null_map));
399
                break;
400
            case PrimitiveType::TYPE_BOOLEAN:
401
                RETURN_IF_ERROR(Impl::template vector<ColumnUInt8>(
402
                        offset_column_data, nested_column, nested_null_map, res, null_map));
403
                break;
404
            case PrimitiveType::TYPE_SMALLINT:
405
                RETURN_IF_ERROR(Impl::template vector<ColumnInt16>(
406
                        offset_column_data, nested_column, nested_null_map, res, null_map));
407
                break;
408
            case PrimitiveType::TYPE_INT:
409
                RETURN_IF_ERROR(Impl::template vector<ColumnInt32>(
410
                        offset_column_data, nested_column, nested_null_map, res, null_map));
411
                break;
412
            case PrimitiveType::TYPE_BIGINT:
413
                RETURN_IF_ERROR(Impl::template vector<ColumnInt64>(
414
                        offset_column_data, nested_column, nested_null_map, res, null_map));
415
                break;
416
            default:
417
                return Status::RuntimeError("Illegal column {} of argument of function {}",
418
                                            block.get_by_position(arguments[0]).column->get_name(),
419
                                            get_name());
420
            }
421
        } else {
422
            return Status::RuntimeError("Illegal column {} of argument of function {}",
423
                                        block.get_by_position(arguments[0]).column->get_name(),
424
                                        get_name());
425
        }
426
2
        block.get_by_position(result).column =
427
2
                ColumnNullable::create(std::move(res_data_column), std::move(res_null_map));
428
2
        return Status::OK();
429
2
    }
_ZNK5doris24FunctionBitmapAlwaysNullINS_16BitmapFromBase64EE12execute_implEPNS_15FunctionContextERNS_5BlockERKSt6vectorIjSaIjEEjm
Line
Count
Source
372
6
                        uint32_t result, size_t input_rows_count) const override {
373
6
        auto res_null_map = ColumnUInt8::create(input_rows_count, 0);
374
6
        auto res_data_column = ColumnBitmap::create();
375
6
        auto& null_map = res_null_map->get_data();
376
6
        auto& res = res_data_column->get_data();
377
378
6
        ColumnPtr& argument_column = block.get_by_position(arguments[0]).column;
379
6
        if constexpr (std::is_same_v<typename Impl::ArgumentType, DataTypeString>) {
380
6
            const auto& str_column = static_cast<const ColumnString&>(*argument_column);
381
6
            const ColumnString::Chars& data = str_column.get_chars();
382
6
            const ColumnString::Offsets& offsets = str_column.get_offsets();
383
6
            RETURN_IF_ERROR(Impl::vector(data, offsets, res, null_map, input_rows_count));
384
        } else if constexpr (std::is_same_v<typename Impl::ArgumentType, DataTypeArray>) {
385
            auto argument_type = remove_nullable(
386
                    assert_cast<const DataTypeArray&>(*block.get_by_position(arguments[0]).type)
387
                            .get_nested_type());
388
            const auto& array_column = static_cast<const ColumnArray&>(*argument_column);
389
            const auto& offset_column_data = array_column.get_offsets();
390
            const auto& nested_nullable_column =
391
                    static_cast<const ColumnNullable&>(array_column.get_data());
392
            const auto& nested_column = nested_nullable_column.get_nested_column();
393
            const auto& nested_null_map = nested_nullable_column.get_null_map_column().get_data();
394
395
            switch (argument_type->get_primitive_type()) {
396
            case PrimitiveType::TYPE_TINYINT:
397
                RETURN_IF_ERROR(Impl::template vector<ColumnInt8>(offset_column_data, nested_column,
398
                                                                  nested_null_map, res, null_map));
399
                break;
400
            case PrimitiveType::TYPE_BOOLEAN:
401
                RETURN_IF_ERROR(Impl::template vector<ColumnUInt8>(
402
                        offset_column_data, nested_column, nested_null_map, res, null_map));
403
                break;
404
            case PrimitiveType::TYPE_SMALLINT:
405
                RETURN_IF_ERROR(Impl::template vector<ColumnInt16>(
406
                        offset_column_data, nested_column, nested_null_map, res, null_map));
407
                break;
408
            case PrimitiveType::TYPE_INT:
409
                RETURN_IF_ERROR(Impl::template vector<ColumnInt32>(
410
                        offset_column_data, nested_column, nested_null_map, res, null_map));
411
                break;
412
            case PrimitiveType::TYPE_BIGINT:
413
                RETURN_IF_ERROR(Impl::template vector<ColumnInt64>(
414
                        offset_column_data, nested_column, nested_null_map, res, null_map));
415
                break;
416
            default:
417
                return Status::RuntimeError("Illegal column {} of argument of function {}",
418
                                            block.get_by_position(arguments[0]).column->get_name(),
419
                                            get_name());
420
            }
421
        } else {
422
            return Status::RuntimeError("Illegal column {} of argument of function {}",
423
                                        block.get_by_position(arguments[0]).column->get_name(),
424
                                        get_name());
425
        }
426
6
        block.get_by_position(result).column =
427
6
                ColumnNullable::create(std::move(res_data_column), std::move(res_null_map));
428
6
        return Status::OK();
429
6
    }
Unexecuted instantiation: _ZNK5doris24FunctionBitmapAlwaysNullINS_15BitmapFromArrayEE12execute_implEPNS_15FunctionContextERNS_5BlockERKSt6vectorIjSaIjEEjm
430
};
431
432
template <int HashBits>
433
struct BitmapHashName {};
434
435
template <>
436
struct BitmapHashName<32> {
437
    static constexpr auto name = "bitmap_hash";
438
};
439
440
template <>
441
struct BitmapHashName<64> {
442
    static constexpr auto name = "bitmap_hash64";
443
};
444
445
template <int HashBits>
446
struct BitmapHash {
447
    static constexpr auto name = BitmapHashName<HashBits>::name;
448
449
    using ReturnType = DataTypeBitMap;
450
451
    template <typename ColumnType>
452
0
    static void vector(const ColumnType* col, MutableColumnPtr& col_res) {
453
0
        if constexpr (std::is_same_v<ColumnType, ColumnString>) {
454
0
            const ColumnString::Chars& data = col->get_chars();
455
0
            const ColumnString::Offsets& offsets = col->get_offsets();
456
0
            auto* res_column = reinterpret_cast<ColumnBitmap*>(col_res.get());
457
0
            auto& res_data = res_column->get_data();
458
0
            size_t size = offsets.size();
459
460
0
            for (size_t i = 0; i < size; ++i) {
461
0
                const char* raw_str = reinterpret_cast<const char*>(&data[offsets[i - 1]]);
462
0
                size_t str_size = offsets[i] - offsets[i - 1];
463
0
                if constexpr (HashBits == 32) {
464
0
                    uint32_t hash_value =
465
0
                            HashUtil::murmur_hash3_32(raw_str, str_size, HashUtil::MURMUR3_32_SEED);
466
0
                    res_data[i].add(hash_value);
467
0
                } else {
468
0
                    uint64_t hash_value = 0;
469
0
                    murmur_hash3_x64_64(raw_str, str_size, 0, &hash_value);
470
0
                    res_data[i].add(hash_value);
471
0
                }
472
0
            }
473
0
        }
474
0
    }
Unexecuted instantiation: _ZN5doris10BitmapHashILi32EE6vectorINS_9ColumnStrIjEEEEvPKT_RNS_3COWINS_7IColumnEE11mutable_ptrIS9_EE
Unexecuted instantiation: _ZN5doris10BitmapHashILi32EE6vectorINS_12ColumnVectorILNS_13PrimitiveTypeE6EEEEEvPKT_RNS_3COWINS_7IColumnEE11mutable_ptrISA_EE
Unexecuted instantiation: _ZN5doris10BitmapHashILi64EE6vectorINS_9ColumnStrIjEEEEvPKT_RNS_3COWINS_7IColumnEE11mutable_ptrIS9_EE
Unexecuted instantiation: _ZN5doris10BitmapHashILi64EE6vectorINS_12ColumnVectorILNS_13PrimitiveTypeE6EEEEEvPKT_RNS_3COWINS_7IColumnEE11mutable_ptrISA_EE
475
476
    template <typename ColumnType>
477
    static void vector_nullable(const ColumnType* col, const NullMap& nullmap,
478
0
                                MutableColumnPtr& col_res) {
479
0
        if constexpr (std::is_same_v<ColumnType, ColumnString>) {
480
0
            const ColumnString::Chars& data = col->get_chars();
481
0
            const ColumnString::Offsets& offsets = col->get_offsets();
482
0
            auto* res_column = reinterpret_cast<ColumnBitmap*>(col_res.get());
483
0
            auto& res_data = res_column->get_data();
484
0
            size_t size = offsets.size();
485
486
0
            for (size_t i = 0; i < size; ++i) {
487
0
                if (nullmap[i]) {
488
0
                    continue;
489
0
                } else {
490
0
                    const char* raw_str = reinterpret_cast<const char*>(&data[offsets[i - 1]]);
491
0
                    size_t str_size = offsets[i] - offsets[i - 1];
492
0
                    if constexpr (HashBits == 32) {
493
0
                        uint32_t hash_value = HashUtil::murmur_hash3_32(raw_str, str_size,
494
0
                                                                        HashUtil::MURMUR3_32_SEED);
495
0
                        res_data[i].add(hash_value);
496
0
                    } else {
497
0
                        uint64_t hash_value = 0;
498
0
                        murmur_hash3_x64_64(raw_str, str_size, 0, &hash_value);
499
0
                        res_data[i].add(hash_value);
500
0
                    }
501
0
                }
502
0
            }
503
0
        }
504
0
    }
Unexecuted instantiation: _ZN5doris10BitmapHashILi32EE15vector_nullableINS_9ColumnStrIjEEEEvPKT_RKNS_8PODArrayIhLm4096ENS_9AllocatorILb0ELb0ELb0ENS_22DefaultMemoryAllocatorELb1EEELm16ELm15EEERNS_3COWINS_7IColumnEE11mutable_ptrISG_EE
Unexecuted instantiation: _ZN5doris10BitmapHashILi32EE15vector_nullableINS_12ColumnVectorILNS_13PrimitiveTypeE6EEEEEvPKT_RKNS_8PODArrayIhLm4096ENS_9AllocatorILb0ELb0ELb0ENS_22DefaultMemoryAllocatorELb1EEELm16ELm15EEERNS_3COWINS_7IColumnEE11mutable_ptrISH_EE
Unexecuted instantiation: _ZN5doris10BitmapHashILi64EE15vector_nullableINS_9ColumnStrIjEEEEvPKT_RKNS_8PODArrayIhLm4096ENS_9AllocatorILb0ELb0ELb0ENS_22DefaultMemoryAllocatorELb1EEELm16ELm15EEERNS_3COWINS_7IColumnEE11mutable_ptrISG_EE
Unexecuted instantiation: _ZN5doris10BitmapHashILi64EE15vector_nullableINS_12ColumnVectorILNS_13PrimitiveTypeE6EEEEEvPKT_RKNS_8PODArrayIhLm4096ENS_9AllocatorILb0ELb0ELb0ENS_22DefaultMemoryAllocatorELb1EEELm16ELm15EEERNS_3COWINS_7IColumnEE11mutable_ptrISH_EE
505
};
506
507
class FunctionBitmapCount : public IFunction {
508
public:
509
    static constexpr auto name = "bitmap_count";
510
511
1
    String get_name() const override { return name; }
512
513
2
    static FunctionPtr create() { return std::make_shared<FunctionBitmapCount>(); }
514
515
0
    DataTypePtr get_return_type_impl(const DataTypes& arguments) const override {
516
0
        return std::make_shared<DataTypeInt64>();
517
0
    }
518
519
0
    size_t get_number_of_arguments() const override { return 1; }
520
521
0
    bool use_default_implementation_for_nulls() const override { return false; }
522
523
    Status execute_impl(FunctionContext* context, Block& block, const ColumnNumbers& arguments,
524
0
                        uint32_t result, size_t input_rows_count) const override {
525
0
        auto res_data_column = ColumnInt64::create();
526
0
        auto& res = res_data_column->get_data();
527
0
        auto data_null_map = ColumnUInt8::create(input_rows_count, 0);
528
0
        auto& null_map = data_null_map->get_data();
529
530
0
        auto column = block.get_by_position(arguments[0]).column;
531
0
        if (auto* nullable = check_and_get_column<const ColumnNullable>(*column)) {
532
0
            VectorizedUtils::update_null_map(null_map, nullable->get_null_map_data());
533
0
            column = nullable->get_nested_column_ptr();
534
0
        }
535
0
        auto str_col = assert_cast<const ColumnBitmap*>(column.get());
536
0
        const auto& col_data = str_col->get_data();
537
538
0
        res.reserve(input_rows_count);
539
0
        for (size_t i = 0; i < input_rows_count; ++i) {
540
0
            if (null_map[i]) {
541
0
                res.push_back(0);
542
0
                continue;
543
0
            }
544
0
            res.push_back(col_data[i].cardinality());
545
0
        }
546
0
        block.replace_by_position(result, std::move(res_data_column));
547
0
        return Status::OK();
548
0
    }
549
};
550
551
struct NameBitmapNot {
552
    static constexpr auto name = "bitmap_not";
553
};
554
555
template <typename LeftDataType, typename RightDataType>
556
struct BitmapNot {
557
    using ResultDataType = DataTypeBitMap;
558
    using T0 = typename LeftDataType::FieldType;
559
    using T1 = typename RightDataType::FieldType;
560
    using TData = std::vector<BitmapValue>;
561
562
0
    static void vector_vector(const TData& lvec, const TData& rvec, TData& res) {
563
0
        size_t size = lvec.size();
564
0
        for (size_t i = 0; i < size; ++i) {
565
0
            res[i] = lvec[i];
566
0
            res[i] -= rvec[i];
567
0
        }
568
0
    }
569
0
    static void vector_scalar(const TData& lvec, const BitmapValue& rval, TData& res) {
570
0
        size_t size = lvec.size();
571
0
        for (size_t i = 0; i < size; ++i) {
572
0
            res[i] = lvec[i];
573
0
            res[i] -= rval;
574
0
        }
575
0
    }
576
0
    static void scalar_vector(const BitmapValue& lval, const TData& rvec, TData& res) {
577
0
        size_t size = rvec.size();
578
0
        for (size_t i = 0; i < size; ++i) {
579
0
            res[i] = lval;
580
0
            res[i] -= rvec[i];
581
0
        }
582
0
    }
583
};
584
585
struct NameBitmapAndNot {
586
    static constexpr auto name = "bitmap_and_not";
587
};
588
589
template <typename LeftDataType, typename RightDataType>
590
struct BitmapAndNot {
591
    using ResultDataType = DataTypeBitMap;
592
    using T0 = typename LeftDataType::FieldType;
593
    using T1 = typename RightDataType::FieldType;
594
    using TData = std::vector<BitmapValue>;
595
596
0
    static void vector_vector(const TData& lvec, const TData& rvec, TData& res) {
597
0
        size_t size = lvec.size();
598
0
        BitmapValue mid_data;
599
0
        for (size_t i = 0; i < size; ++i) {
600
0
            mid_data = lvec[i];
601
0
            mid_data &= rvec[i];
602
0
            res[i] = lvec[i];
603
0
            res[i] -= mid_data;
604
0
            mid_data.reset();
605
0
        }
606
0
    }
607
0
    static void vector_scalar(const TData& lvec, const BitmapValue& rval, TData& res) {
608
0
        size_t size = lvec.size();
609
0
        BitmapValue mid_data;
610
0
        for (size_t i = 0; i < size; ++i) {
611
0
            mid_data = lvec[i];
612
0
            mid_data &= rval;
613
0
            res[i] = lvec[i];
614
0
            res[i] -= mid_data;
615
0
            mid_data.reset();
616
0
        }
617
0
    }
618
0
    static void scalar_vector(const BitmapValue& lval, const TData& rvec, TData& res) {
619
0
        size_t size = rvec.size();
620
0
        BitmapValue mid_data;
621
0
        for (size_t i = 0; i < size; ++i) {
622
0
            mid_data = lval;
623
0
            mid_data &= rvec[i];
624
0
            res[i] = lval;
625
0
            res[i] -= mid_data;
626
0
            mid_data.reset();
627
0
        }
628
0
    }
629
};
630
631
struct NameBitmapAndNotCount {
632
    static constexpr auto name = "bitmap_and_not_count";
633
};
634
635
template <typename LeftDataType, typename RightDataType>
636
struct BitmapAndNotCount {
637
    using ResultDataType = DataTypeInt64;
638
    using T0 = typename LeftDataType::FieldType;
639
    using T1 = typename RightDataType::FieldType;
640
    using TData = std::vector<BitmapValue>;
641
    using ResTData = typename ColumnInt64::Container::value_type;
642
643
2
    static void vector_vector(const TData& lvec, const TData& rvec, ResTData* res) {
644
2
        size_t size = lvec.size();
645
2
        BitmapValue mid_data;
646
10
        for (size_t i = 0; i < size; ++i) {
647
8
            mid_data = lvec[i];
648
8
            mid_data &= rvec[i];
649
8
            res[i] = lvec[i].andnot_cardinality(mid_data);
650
8
            mid_data.reset();
651
8
        }
652
2
    }
653
0
    static void scalar_vector(const BitmapValue& lval, const TData& rvec, ResTData* res) {
654
0
        size_t size = rvec.size();
655
0
        BitmapValue mid_data;
656
0
        for (size_t i = 0; i < size; ++i) {
657
0
            mid_data = lval;
658
0
            mid_data &= rvec[i];
659
0
            res[i] = lval.andnot_cardinality(mid_data);
660
0
            mid_data.reset();
661
0
        }
662
0
    }
663
0
    static void vector_scalar(const TData& lvec, const BitmapValue& rval, ResTData* res) {
664
0
        size_t size = lvec.size();
665
0
        BitmapValue mid_data;
666
0
        for (size_t i = 0; i < size; ++i) {
667
0
            mid_data = lvec[i];
668
0
            mid_data &= rval;
669
0
            res[i] = lvec[i].andnot_cardinality(mid_data);
670
0
            mid_data.reset();
671
0
        }
672
0
    }
673
};
674
675
14
void update_bitmap_op_count(int64_t* __restrict count, const NullMap& null_map) {
676
14
    static constexpr int64_t flags[2] = {-1, 0};
677
14
    size_t size = null_map.size();
678
14
    auto* __restrict null_map_data = null_map.data();
679
66
    for (size_t i = 0; i < size; ++i) {
680
52
        count[i] &= flags[null_map_data[i]];
681
52
    }
682
14
}
683
684
// for bitmap_and_count, bitmap_xor_count and bitmap_and_not_count,
685
// result is 0 for rows that if any column is null value
686
ColumnPtr handle_bitmap_op_count_null_value(ColumnPtr& src, const Block& block,
687
                                            const ColumnNumbers& args, uint32_t result,
688
6
                                            size_t input_rows_count) {
689
6
    MutableColumnPtr mutable_src = IColumn::mutate(std::move(src));
690
6
    auto* nullable = assert_cast<ColumnNullable*>(mutable_src.get());
691
6
    auto* src_not_nullable_mutable = &nullable->get_nested_column();
692
6
    auto* __restrict count_data =
693
6
            assert_cast<ColumnInt64*>(src_not_nullable_mutable)->get_data().data();
694
695
14
    for (const auto& arg : args) {
696
14
        const ColumnWithTypeAndName& elem = block.get_by_position(arg);
697
14
        if (!elem.type->is_nullable()) {
698
0
            continue;
699
0
        }
700
701
14
        bool is_const = is_column_const(*elem.column);
702
        /// Const Nullable that are NULL.
703
14
        if (is_const && assert_cast<const ColumnConst*>(elem.column.get())->only_null()) {
704
0
            return block.get_by_position(result).type->create_column_const(
705
0
                    input_rows_count, Field::create_field<TYPE_BIGINT>(0));
706
0
        }
707
14
        if (is_const) {
708
0
            continue;
709
0
        }
710
711
14
        if (const auto* nullable_column = assert_cast<const ColumnNullable*>(elem.column.get())) {
712
14
            const ColumnPtr& null_map_column = nullable_column->get_null_map_column_ptr();
713
14
            const NullMap& src_null_map =
714
14
                    assert_cast<const ColumnUInt8&>(*null_map_column).get_data();
715
716
14
            update_bitmap_op_count(count_data, src_null_map);
717
14
        }
718
14
    }
719
720
6
    return mutable_src;
721
6
}
722
723
Status execute_bitmap_op_count_null_to_zero(
724
        FunctionContext* context, Block& block, const ColumnNumbers& arguments, uint32_t result,
725
        size_t input_rows_count,
726
        const std::function<Status(FunctionContext*, Block&, const ColumnNumbers&, size_t, size_t)>&
727
6
                exec_impl_func) {
728
6
    if (have_null_column(block, arguments)) {
729
6
        auto [temporary_block, new_args, new_result] =
730
6
                create_block_with_nested_columns(block, arguments, result);
731
6
        RETURN_IF_ERROR(exec_impl_func(context, temporary_block, new_args, new_result,
732
6
                                       temporary_block.rows()));
733
6
        block.get_by_position(result).column = handle_bitmap_op_count_null_value(
734
6
                temporary_block.get_by_position(new_result).column, block, arguments, result,
735
6
                input_rows_count);
736
6
    } else {
737
0
        return exec_impl_func(context, block, arguments, result, input_rows_count);
738
0
    }
739
6
    return Status::OK();
740
6
}
741
742
template <typename FunctionName>
743
class FunctionBitmapAndNotCount : public IFunction {
744
public:
745
    using LeftDataType = DataTypeBitMap;
746
    using RightDataType = DataTypeBitMap;
747
    using ResultDataType = typename BitmapAndNotCount<LeftDataType, RightDataType>::ResultDataType;
748
749
    static constexpr auto name = FunctionName::name;
750
4
    static FunctionPtr create() { return std::make_shared<FunctionBitmapAndNotCount>(); }
751
1
    String get_name() const override { return name; }
752
2
    size_t get_number_of_arguments() const override { return 2; }
753
2
    DataTypePtr get_return_type_impl(const DataTypes& arguments) const override {
754
2
        bool return_nullable = false;
755
        // result is nullable only when any columns is nullable for bitmap_and_not_count
756
2
        for (size_t i = 0; i < arguments.size(); ++i) {
757
2
            if (arguments[i]->is_nullable()) {
758
2
                return_nullable = true;
759
2
                break;
760
2
            }
761
2
        }
762
2
        auto result_type = std::make_shared<ResultDataType>();
763
2
        return return_nullable ? make_nullable(result_type) : result_type;
764
2
    }
765
766
4
    bool use_default_implementation_for_nulls() const override {
767
        // for bitmap_and_not_count, result is always not null, and if the bitmap op result is null,
768
        // the count is 0
769
4
        return false;
770
4
    }
771
772
    Status execute_impl(FunctionContext* context, Block& block, const ColumnNumbers& arguments,
773
2
                        uint32_t result, size_t input_rows_count) const override {
774
2
        DCHECK_EQ(arguments.size(), 2);
775
2
        auto impl_func = [&](FunctionContext* context, Block& block, const ColumnNumbers& arguments,
776
2
                             uint32_t result, size_t input_rows_count) {
777
2
            return execute_impl_internal(context, block, arguments, result, input_rows_count);
778
2
        };
779
2
        return execute_bitmap_op_count_null_to_zero(context, block, arguments, result,
780
2
                                                    input_rows_count, impl_func);
781
2
    }
782
783
    Status execute_impl_internal(FunctionContext* context, Block& block,
784
                                 const ColumnNumbers& arguments, uint32_t result,
785
2
                                 size_t input_rows_count) const {
786
2
        using ColVecResult = ColumnVector<ResultDataType::PType>;
787
788
2
        typename ColVecResult::MutablePtr col_res = ColVecResult::create();
789
2
        auto& vec_res = col_res->get_data();
790
2
        vec_res.resize(block.rows());
791
792
2
        const auto& left = block.get_by_position(arguments[0]);
793
2
        auto lcol = left.column;
794
2
        const auto& right = block.get_by_position(arguments[1]);
795
2
        auto rcol = right.column;
796
797
2
        if (is_column_const(*left.column)) {
798
0
            BitmapAndNotCount<LeftDataType, RightDataType>::scalar_vector(
799
0
                    assert_cast<const ColumnBitmap&>(
800
0
                            assert_cast<const ColumnConst*>(lcol.get())->get_data_column())
801
0
                            .get_data()[0],
802
0
                    assert_cast<const ColumnBitmap*>(rcol.get())->get_data(), vec_res.data());
803
2
        } else if (is_column_const(*right.column)) {
804
0
            BitmapAndNotCount<LeftDataType, RightDataType>::vector_scalar(
805
0
                    assert_cast<const ColumnBitmap*>(lcol.get())->get_data(),
806
0
                    assert_cast<const ColumnBitmap&>(
807
0
                            assert_cast<const ColumnConst*>(rcol.get())->get_data_column())
808
0
                            .get_data()[0],
809
0
                    vec_res.data());
810
2
        } else {
811
2
            BitmapAndNotCount<LeftDataType, RightDataType>::vector_vector(
812
2
                    assert_cast<const ColumnBitmap*>(lcol.get())->get_data(),
813
2
                    assert_cast<const ColumnBitmap*>(rcol.get())->get_data(), vec_res.data());
814
2
        }
815
816
2
        auto& result_info = block.get_by_position(result);
817
2
        if (result_info.type->is_nullable()) {
818
2
            block.replace_by_position(
819
2
                    result, ColumnNullable::create(std::move(col_res),
820
2
                                                   ColumnUInt8::create(input_rows_count, 0)));
821
2
        } else {
822
0
            block.replace_by_position(result, std::move(col_res));
823
0
        }
824
2
        return Status::OK();
825
2
    }
826
};
827
828
struct NameBitmapContains {
829
    static constexpr auto name = "bitmap_contains";
830
};
831
832
template <typename LeftDataType, typename RightDataType>
833
struct BitmapContains {
834
    using ResultDataType = DataTypeUInt8;
835
    using T0 = typename LeftDataType::FieldType;
836
    using T1 = typename RightDataType::FieldType;
837
    using LTData = std::vector<BitmapValue>;
838
    using RTData = typename ColumnVector<RightDataType::PType>::Container;
839
    using ResTData = typename ColumnUInt8::Container;
840
841
0
    static void vector_vector(const LTData& lvec, const RTData& rvec, ResTData& res) {
842
0
        size_t size = lvec.size();
843
0
        for (size_t i = 0; i < size; ++i) {
844
0
            res[i] = lvec[i].contains(rvec[i]);
845
0
        }
846
0
    }
847
0
    static void vector_scalar(const LTData& lvec, const T1& rval, ResTData& res) {
848
0
        size_t size = lvec.size();
849
0
        for (size_t i = 0; i < size; ++i) {
850
0
            res[i] = lvec[i].contains(rval);
851
0
        }
852
0
    }
853
0
    static void scalar_vector(const BitmapValue& lval, const RTData& rvec, ResTData& res) {
854
0
        size_t size = rvec.size();
855
0
        for (size_t i = 0; i < size; ++i) {
856
0
            res[i] = lval.contains(rvec[i]);
857
0
        }
858
0
    }
859
};
860
861
struct NameBitmapRemove {
862
    static constexpr auto name = "bitmap_remove";
863
};
864
865
template <typename LeftDataType, typename RightDataType>
866
struct BitmapRemove {
867
    using ResultDataType = DataTypeBitMap;
868
    using T0 = typename LeftDataType::FieldType;
869
    using T1 = typename RightDataType::FieldType;
870
    using LTData = std::vector<BitmapValue>;
871
    using RTData = typename ColumnVector<RightDataType::PType>::Container;
872
    using ResTData = std::vector<BitmapValue>;
873
874
1
    static void vector_vector(const LTData& lvec, const RTData& rvec, ResTData& res) {
875
1
        size_t size = lvec.size();
876
4
        for (size_t i = 0; i < size; ++i) {
877
3
            res[i] = lvec[i];
878
3
            res[i].remove(rvec[i]);
879
3
        }
880
1
    }
881
0
    static void vector_scalar(const LTData& lvec, const T1& rval, ResTData& res) {
882
0
        size_t size = lvec.size();
883
0
        for (size_t i = 0; i < size; ++i) {
884
0
            res[i] = lvec[i];
885
0
            res[i].remove(rval);
886
0
        }
887
0
    }
888
0
    static void scalar_vector(const BitmapValue& lval, const RTData& rvec, ResTData& res) {
889
0
        size_t size = rvec.size();
890
0
        for (size_t i = 0; i < size; ++i) {
891
0
            res[i] = lval;
892
0
            res[i].remove(rvec[i]);
893
0
        }
894
0
    }
895
};
896
897
struct NameBitmapHasAny {
898
    static constexpr auto name = "bitmap_has_any";
899
};
900
901
template <typename LeftDataType, typename RightDataType>
902
struct BitmapHasAny {
903
    using ResultDataType = DataTypeUInt8;
904
    using T0 = typename LeftDataType::FieldType;
905
    using T1 = typename RightDataType::FieldType;
906
    using TData = std::vector<BitmapValue>;
907
    using ResTData = typename ColumnUInt8::Container;
908
909
0
    static void vector_vector(const TData& lvec, const TData& rvec, ResTData& res) {
910
0
        size_t size = lvec.size();
911
0
        for (size_t i = 0; i < size; ++i) {
912
0
            res[i] = lvec[i].intersects(rvec[i]);
913
0
        }
914
0
    }
915
0
    static void vector_scalar(const TData& lvec, const BitmapValue& rval, ResTData& res) {
916
0
        size_t size = lvec.size();
917
0
        for (size_t i = 0; i < size; ++i) {
918
0
            res[i] = lvec[i].intersects(rval);
919
0
        }
920
0
    }
921
0
    static void scalar_vector(const BitmapValue& lval, const TData& rvec, ResTData& res) {
922
0
        size_t size = rvec.size();
923
0
        for (size_t i = 0; i < size; ++i) {
924
0
            res[i] = lval.intersects(rvec[i]);
925
0
        }
926
0
    }
927
};
928
929
struct NameBitmapHasAll {
930
    static constexpr auto name = "bitmap_has_all";
931
};
932
933
template <typename LeftDataType, typename RightDataType>
934
struct BitmapHasAll {
935
    using ResultDataType = DataTypeUInt8;
936
    using T0 = typename LeftDataType::FieldType;
937
    using T1 = typename RightDataType::FieldType;
938
    using TData = std::vector<BitmapValue>;
939
    using ResTData = typename ColumnUInt8::Container;
940
941
1
    static void vector_vector(const TData& lvec, const TData& rvec, ResTData& res) {
942
1
        size_t size = lvec.size();
943
6
        for (size_t i = 0; i < size; ++i) {
944
5
            res[i] = lvec[i].contains_all(rvec[i]);
945
5
        }
946
1
    }
947
0
    static void vector_scalar(const TData& lvec, const BitmapValue& rval, ResTData& res) {
948
0
        size_t size = lvec.size();
949
0
        for (size_t i = 0; i < size; ++i) {
950
0
            res[i] = lvec[i].contains_all(rval);
951
0
        }
952
0
    }
953
0
    static void scalar_vector(const BitmapValue& lval, const TData& rvec, ResTData& res) {
954
0
        size_t size = rvec.size();
955
0
        for (size_t i = 0; i < size; ++i) {
956
0
            res[i] = lval.contains_all(rvec[i]);
957
0
        }
958
0
    }
959
};
960
961
struct NameBitmapToString {
962
    static constexpr auto name = "bitmap_to_string";
963
};
964
965
struct BitmapToString {
966
    using ReturnType = DataTypeString;
967
    static constexpr auto PrimitiveTypeImpl = PrimitiveType::TYPE_BITMAP;
968
    using Type = DataTypeBitMap::FieldType;
969
    using ReturnColumnType = ColumnString;
970
    using Chars = ColumnString::Chars;
971
    using Offsets = ColumnString::Offsets;
972
973
1
    static Status vector(const std::vector<BitmapValue>& data, Chars& chars, Offsets& offsets) {
974
1
        size_t size = data.size();
975
1
        offsets.resize(size);
976
1
        chars.reserve(size);
977
5
        for (size_t i = 0; i < size; ++i) {
978
4
            StringOP::push_value_string(data[i].to_string(), i, chars, offsets);
979
4
        }
980
1
        return Status::OK();
981
1
    }
982
};
983
984
struct NameBitmapToBase64 {
985
    static constexpr auto name = "bitmap_to_base64";
986
};
987
988
struct BitmapToBase64 {
989
    using ReturnType = DataTypeString;
990
    static constexpr auto PrimitiveTypeImpl = PrimitiveType::TYPE_BITMAP;
991
    using Type = DataTypeBitMap::FieldType;
992
    using ReturnColumnType = ColumnString;
993
    using Chars = ColumnString::Chars;
994
    using Offsets = ColumnString::Offsets;
995
996
    // ColumnString not support 64bit, only 32bit, so that the max size is 4G
997
5
    static Status vector(const std::vector<BitmapValue>& data, Chars& chars, Offsets& offsets) {
998
5
        size_t size = data.size();
999
5
        offsets.resize(size);
1000
5
        size_t output_char_size = 0;
1001
24
        for (size_t i = 0; i < size; ++i) {
1002
19
            const BitmapValue& bitmap_val = data[i];
1003
19
            auto ser_size = bitmap_val.getSizeInBytes();
1004
19
            output_char_size += (int)(4.0 * ceil((double)ser_size / 3.0));
1005
19
        }
1006
5
        ColumnString::check_chars_length(output_char_size, size);
1007
5
        chars.resize(output_char_size);
1008
5
        auto chars_data = chars.data();
1009
1010
5
        size_t cur_ser_size = 0;
1011
5
        size_t last_ser_size = 0;
1012
5
        std::string ser_buff;
1013
5
        size_t encoded_offset = 0;
1014
24
        for (size_t i = 0; i < size; ++i) {
1015
19
            const BitmapValue& bitmap_val = data[i];
1016
19
            cur_ser_size = bitmap_val.getSizeInBytes();
1017
19
            if (cur_ser_size > last_ser_size) {
1018
10
                last_ser_size = cur_ser_size;
1019
10
                ser_buff.resize(cur_ser_size);
1020
10
            }
1021
19
            bitmap_val.write_to(ser_buff.data());
1022
1023
19
            auto outlen = base64_encode((const unsigned char*)ser_buff.data(), cur_ser_size,
1024
19
                                        chars_data + encoded_offset);
1025
19
            DCHECK(outlen > 0);
1026
1027
19
            encoded_offset += (int)(4.0 * ceil((double)cur_ser_size / 3.0));
1028
19
            offsets[i] = cast_set<UInt32>(encoded_offset);
1029
19
        }
1030
5
        return Status::OK();
1031
5
    }
1032
};
1033
1034
struct SubBitmap {
1035
    static constexpr auto name = "sub_bitmap";
1036
    using TData1 = std::vector<BitmapValue>;
1037
    using TData2 = typename ColumnInt64::Container;
1038
1039
    static void vector3(const TData1& bitmap_data, const TData2& offset_data,
1040
                        const TData2& limit_data, NullMap& null_map, size_t input_rows_count,
1041
0
                        TData1& res) {
1042
0
        for (int i = 0; i < input_rows_count; ++i) {
1043
0
            if (null_map[i]) {
1044
0
                continue;
1045
0
            }
1046
0
            if (limit_data[i] <= 0) {
1047
0
                null_map[i] = 1;
1048
0
                continue;
1049
0
            }
1050
0
            if (bitmap_data[i].offset_limit(offset_data[i], limit_data[i], &res[i]) == 0) {
1051
0
                null_map[i] = 1;
1052
0
            }
1053
0
        }
1054
0
    }
1055
    static void vector_scalars(const TData1& bitmap_data, const Int64& offset_data,
1056
                               const Int64& limit_data, NullMap& null_map, size_t input_rows_count,
1057
0
                               TData1& res) {
1058
0
        for (int i = 0; i < input_rows_count; ++i) {
1059
0
            if (null_map[i]) {
1060
0
                continue;
1061
0
            }
1062
0
            if (limit_data <= 0) {
1063
0
                null_map[i] = 1;
1064
0
                continue;
1065
0
            }
1066
0
            if (bitmap_data[i].offset_limit(offset_data, limit_data, &res[i]) == 0) {
1067
0
                null_map[i] = 1;
1068
0
            }
1069
0
        }
1070
0
    }
1071
};
1072
1073
struct BitmapSubsetLimit {
1074
    static constexpr auto name = "bitmap_subset_limit";
1075
    using TData1 = std::vector<BitmapValue>;
1076
    using TData2 = typename ColumnInt64::Container;
1077
1078
    static void vector3(const TData1& bitmap_data, const TData2& offset_data,
1079
                        const TData2& limit_data, NullMap& null_map, size_t input_rows_count,
1080
0
                        TData1& res) {
1081
0
        for (int i = 0; i < input_rows_count; ++i) {
1082
0
            if (null_map[i]) {
1083
0
                continue;
1084
0
            }
1085
0
            if (offset_data[i] < 0 || limit_data[i] < 0) {
1086
0
                null_map[i] = 1;
1087
0
                continue;
1088
0
            }
1089
0
            bitmap_data[i].sub_limit(offset_data[i], limit_data[i], &res[i]);
1090
0
        }
1091
0
    }
1092
    static void vector_scalars(const TData1& bitmap_data, const Int64& offset_data,
1093
                               const Int64& limit_data, NullMap& null_map, size_t input_rows_count,
1094
0
                               TData1& res) {
1095
0
        for (int i = 0; i < input_rows_count; ++i) {
1096
0
            if (null_map[i]) {
1097
0
                continue;
1098
0
            }
1099
0
            if (offset_data < 0 || limit_data < 0) {
1100
0
                null_map[i] = 1;
1101
0
                continue;
1102
0
            }
1103
0
            bitmap_data[i].sub_limit(offset_data, limit_data, &res[i]);
1104
0
        }
1105
0
    }
1106
};
1107
1108
struct BitmapSubsetInRange {
1109
    static constexpr auto name = "bitmap_subset_in_range";
1110
    using TData1 = std::vector<BitmapValue>;
1111
    using TData2 = typename ColumnInt64::Container;
1112
1113
    static void vector3(const TData1& bitmap_data, const TData2& range_start,
1114
                        const TData2& range_end, NullMap& null_map, size_t input_rows_count,
1115
0
                        TData1& res) {
1116
0
        for (int i = 0; i < input_rows_count; ++i) {
1117
0
            if (null_map[i]) {
1118
0
                continue;
1119
0
            }
1120
0
            if (range_start[i] >= range_end[i] || range_start[i] < 0 || range_end[i] < 0) {
1121
0
                null_map[i] = 1;
1122
0
                continue;
1123
0
            }
1124
0
            bitmap_data[i].sub_range(range_start[i], range_end[i], &res[i]);
1125
0
        }
1126
0
    }
1127
    static void vector_scalars(const TData1& bitmap_data, const Int64& range_start,
1128
                               const Int64& range_end, NullMap& null_map, size_t input_rows_count,
1129
0
                               TData1& res) {
1130
0
        for (int i = 0; i < input_rows_count; ++i) {
1131
0
            if (null_map[i]) {
1132
0
                continue;
1133
0
            }
1134
0
            if (range_start >= range_end || range_start < 0 || range_end < 0) {
1135
0
                null_map[i] = 1;
1136
0
                continue;
1137
0
            }
1138
0
            bitmap_data[i].sub_range(range_start, range_end, &res[i]);
1139
0
        }
1140
0
    }
1141
};
1142
1143
template <typename Impl>
1144
class FunctionBitmapSubs : public IFunction {
1145
public:
1146
    static constexpr auto name = Impl::name;
1147
3
    String get_name() const override { return name; }
_ZNK5doris18FunctionBitmapSubsINS_9SubBitmapEE8get_nameB5cxx11Ev
Line
Count
Source
1147
1
    String get_name() const override { return name; }
_ZNK5doris18FunctionBitmapSubsINS_17BitmapSubsetLimitEE8get_nameB5cxx11Ev
Line
Count
Source
1147
1
    String get_name() const override { return name; }
_ZNK5doris18FunctionBitmapSubsINS_19BitmapSubsetInRangeEE8get_nameB5cxx11Ev
Line
Count
Source
1147
1
    String get_name() const override { return name; }
1148
1149
6
    static FunctionPtr create() { return std::make_shared<FunctionBitmapSubs>(); }
_ZN5doris18FunctionBitmapSubsINS_9SubBitmapEE6createEv
Line
Count
Source
1149
2
    static FunctionPtr create() { return std::make_shared<FunctionBitmapSubs>(); }
_ZN5doris18FunctionBitmapSubsINS_17BitmapSubsetLimitEE6createEv
Line
Count
Source
1149
2
    static FunctionPtr create() { return std::make_shared<FunctionBitmapSubs>(); }
_ZN5doris18FunctionBitmapSubsINS_19BitmapSubsetInRangeEE6createEv
Line
Count
Source
1149
2
    static FunctionPtr create() { return std::make_shared<FunctionBitmapSubs>(); }
1150
1151
0
    DataTypePtr get_return_type_impl(const DataTypes& arguments) const override {
1152
0
        return make_nullable(std::make_shared<DataTypeBitMap>());
1153
0
    }
Unexecuted instantiation: _ZNK5doris18FunctionBitmapSubsINS_9SubBitmapEE20get_return_type_implERKSt6vectorISt10shared_ptrIKNS_9IDataTypeEESaIS7_EE
Unexecuted instantiation: _ZNK5doris18FunctionBitmapSubsINS_17BitmapSubsetLimitEE20get_return_type_implERKSt6vectorISt10shared_ptrIKNS_9IDataTypeEESaIS7_EE
Unexecuted instantiation: _ZNK5doris18FunctionBitmapSubsINS_19BitmapSubsetInRangeEE20get_return_type_implERKSt6vectorISt10shared_ptrIKNS_9IDataTypeEESaIS7_EE
1154
1155
0
    size_t get_number_of_arguments() const override { return 3; }
Unexecuted instantiation: _ZNK5doris18FunctionBitmapSubsINS_9SubBitmapEE23get_number_of_argumentsEv
Unexecuted instantiation: _ZNK5doris18FunctionBitmapSubsINS_17BitmapSubsetLimitEE23get_number_of_argumentsEv
Unexecuted instantiation: _ZNK5doris18FunctionBitmapSubsINS_19BitmapSubsetInRangeEE23get_number_of_argumentsEv
1156
1157
    Status execute_impl(FunctionContext* context, Block& block, const ColumnNumbers& arguments,
1158
0
                        uint32_t result, size_t input_rows_count) const override {
1159
0
        DCHECK_EQ(arguments.size(), 3);
1160
0
        auto res_null_map = ColumnUInt8::create(input_rows_count, 0);
1161
0
        auto res_data_column = ColumnBitmap::create(input_rows_count);
1162
1163
0
        bool col_const[3];
1164
0
        ColumnPtr argument_columns[3];
1165
0
        for (int i = 0; i < 3; ++i) {
1166
0
            col_const[i] = is_column_const(*block.get_by_position(arguments[i]).column);
1167
0
        }
1168
0
        argument_columns[0] = col_const[0] ? static_cast<const ColumnConst&>(
1169
0
                                                     *block.get_by_position(arguments[0]).column)
1170
0
                                                     .convert_to_full_column()
1171
0
                                           : block.get_by_position(arguments[0]).column;
1172
1173
0
        default_preprocess_parameter_columns(argument_columns, col_const, {1, 2}, block, arguments);
1174
1175
0
        auto bitmap_column = assert_cast<const ColumnBitmap*>(argument_columns[0].get());
1176
0
        auto offset_column = assert_cast<const ColumnInt64*>(argument_columns[1].get());
1177
0
        auto limit_column = assert_cast<const ColumnInt64*>(argument_columns[2].get());
1178
1179
0
        if (col_const[1] && col_const[2]) {
1180
0
            Impl::vector_scalars(bitmap_column->get_data(), offset_column->get_element(0),
1181
0
                                 limit_column->get_element(0), res_null_map->get_data(),
1182
0
                                 input_rows_count, res_data_column->get_data());
1183
0
        } else {
1184
0
            Impl::vector3(bitmap_column->get_data(), offset_column->get_data(),
1185
0
                          limit_column->get_data(), res_null_map->get_data(), input_rows_count,
1186
0
                          res_data_column->get_data());
1187
0
        }
1188
1189
0
        block.get_by_position(result).column =
1190
0
                ColumnNullable::create(std::move(res_data_column), std::move(res_null_map));
1191
0
        return Status::OK();
1192
0
    }
Unexecuted instantiation: _ZNK5doris18FunctionBitmapSubsINS_9SubBitmapEE12execute_implEPNS_15FunctionContextERNS_5BlockERKSt6vectorIjSaIjEEjm
Unexecuted instantiation: _ZNK5doris18FunctionBitmapSubsINS_17BitmapSubsetLimitEE12execute_implEPNS_15FunctionContextERNS_5BlockERKSt6vectorIjSaIjEEjm
Unexecuted instantiation: _ZNK5doris18FunctionBitmapSubsINS_19BitmapSubsetInRangeEE12execute_implEPNS_15FunctionContextERNS_5BlockERKSt6vectorIjSaIjEEjm
1193
};
1194
1195
class FunctionBitmapToArray : public IFunction {
1196
public:
1197
    static constexpr auto name = "bitmap_to_array";
1198
1199
1
    String get_name() const override { return name; }
1200
1201
2
    static FunctionPtr create() { return std::make_shared<FunctionBitmapToArray>(); }
1202
1203
0
    DataTypePtr get_return_type_impl(const DataTypes& arguments) const override {
1204
0
        auto nested_type = make_nullable(std::make_shared<DataTypeInt64>());
1205
0
        return std::make_shared<DataTypeArray>(nested_type);
1206
0
    }
1207
1208
0
    size_t get_number_of_arguments() const override { return 1; }
1209
1210
    Status execute_impl(FunctionContext* context, Block& block, const ColumnNumbers& arguments,
1211
0
                        uint32_t result, size_t input_rows_count) const override {
1212
0
        auto return_nested_type = make_nullable(std::make_shared<DataTypeInt64>());
1213
0
        auto dest_array_column_ptr = ColumnArray::create(return_nested_type->create_column(),
1214
0
                                                         ColumnArray::ColumnOffsets::create());
1215
1216
0
        IColumn* dest_nested_column = &dest_array_column_ptr->get_data();
1217
0
        ColumnNullable* dest_nested_nullable_col =
1218
0
                reinterpret_cast<ColumnNullable*>(dest_nested_column);
1219
0
        dest_nested_column = dest_nested_nullable_col->get_nested_column_ptr().get();
1220
0
        auto& dest_nested_null_map = dest_nested_nullable_col->get_null_map_column().get_data();
1221
1222
0
        auto& arg_col = block.get_by_position(arguments[0]).column;
1223
0
        auto bitmap_col = assert_cast<const ColumnBitmap*>(arg_col.get());
1224
0
        const auto& bitmap_col_data = bitmap_col->get_data();
1225
0
        auto& nested_column_data = assert_cast<ColumnInt64*>(dest_nested_column)->get_data();
1226
0
        auto& dest_offsets = dest_array_column_ptr->get_offsets();
1227
0
        dest_offsets.reserve(input_rows_count);
1228
1229
0
        for (int i = 0; i < input_rows_count; ++i) {
1230
0
            bitmap_col_data[i].to_array(nested_column_data);
1231
0
            dest_nested_null_map.resize_fill(nested_column_data.size(), 0);
1232
0
            dest_offsets.push_back(nested_column_data.size());
1233
0
        }
1234
1235
0
        block.replace_by_position(result, std::move(dest_array_column_ptr));
1236
0
        return Status::OK();
1237
0
    }
1238
};
1239
1240
using FunctionBitmapEmpty = FunctionConst<BitmapEmpty, false>;
1241
using FunctionToBitmap = FunctionAlwaysNotNullable<ToBitmap>;
1242
using FunctionToBitmapWithCheck = FunctionAlwaysNotNullable<ToBitmapWithCheck, true>;
1243
1244
using FunctionBitmapFromString = FunctionBitmapAlwaysNull<BitmapFromString>;
1245
using FunctionBitmapFromArray = FunctionBitmapAlwaysNull<BitmapFromArray>;
1246
using FunctionBitmapHash = FunctionAlwaysNotNullable<BitmapHash<32>>;
1247
using FunctionBitmapHash64 = FunctionAlwaysNotNullable<BitmapHash<64>>;
1248
1249
using FunctionBitmapMin = FunctionBitmapSingle<FunctionBitmapMinImpl>;
1250
using FunctionBitmapMax = FunctionBitmapSingle<FunctionBitmapMaxImpl>;
1251
1252
using FunctionBitmapToString = FunctionUnaryToType<BitmapToString, NameBitmapToString>;
1253
using FunctionBitmapToBase64 = FunctionUnaryToType<BitmapToBase64, NameBitmapToBase64>;
1254
using FunctionBitmapFromBase64 = FunctionBitmapAlwaysNull<BitmapFromBase64>;
1255
using FunctionBitmapNot =
1256
        FunctionBinaryToType<DataTypeBitMap, DataTypeBitMap, BitmapNot, NameBitmapNot>;
1257
using FunctionBitmapAndNot =
1258
        FunctionBinaryToType<DataTypeBitMap, DataTypeBitMap, BitmapAndNot, NameBitmapAndNot>;
1259
using FunctionBitmapContains =
1260
        FunctionBinaryToType<DataTypeBitMap, DataTypeInt64, BitmapContains, NameBitmapContains>;
1261
using FunctionBitmapRemove =
1262
        FunctionBinaryToType<DataTypeBitMap, DataTypeInt64, BitmapRemove, NameBitmapRemove>;
1263
1264
using FunctionBitmapHasAny =
1265
        FunctionBinaryToType<DataTypeBitMap, DataTypeBitMap, BitmapHasAny, NameBitmapHasAny>;
1266
using FunctionBitmapHasAll =
1267
        FunctionBinaryToType<DataTypeBitMap, DataTypeBitMap, BitmapHasAll, NameBitmapHasAll>;
1268
using FunctionSubBitmap = FunctionBitmapSubs<SubBitmap>;
1269
using FunctionBitmapSubsetLimit = FunctionBitmapSubs<BitmapSubsetLimit>;
1270
using FunctionBitmapSubsetInRange = FunctionBitmapSubs<BitmapSubsetInRange>;
1271
1272
1
void register_function_bitmap(SimpleFunctionFactory& factory) {
1273
1
    factory.register_function<FunctionBitmapEmpty>();
1274
1
    factory.register_function<FunctionToBitmap>();
1275
1
    factory.register_function<FunctionToBitmapWithCheck>();
1276
1
    factory.register_function<FunctionBitmapFromString>();
1277
1
    factory.register_function<FunctionBitmapToBase64>();
1278
1
    factory.register_function<FunctionBitmapFromBase64>();
1279
1
    factory.register_function<FunctionBitmapFromArray>();
1280
1
    factory.register_function<FunctionBitmapHash>();
1281
1
    factory.register_function<FunctionBitmapHash64>();
1282
1
    factory.register_function<FunctionBitmapCount>();
1283
1
    factory.register_function<FunctionBitmapMin>();
1284
1
    factory.register_function<FunctionBitmapMax>();
1285
1
    factory.register_function<FunctionBitmapToString>();
1286
1
    factory.register_function<FunctionBitmapNot>();
1287
1
    factory.register_function<FunctionBitmapAndNot>();
1288
1
    factory.register_alias(NameBitmapAndNot::name, "bitmap_andnot");
1289
1
    factory.register_function<FunctionBitmapAndNotCount<NameBitmapAndNotCount>>();
1290
1
    factory.register_alias(NameBitmapAndNotCount::name, "bitmap_andnot_count");
1291
1
    factory.register_function<FunctionBitmapContains>();
1292
1
    factory.register_function<FunctionBitmapRemove>();
1293
1
    factory.register_function<FunctionBitmapHasAny>();
1294
1
    factory.register_function<FunctionBitmapHasAll>();
1295
1
    factory.register_function<FunctionSubBitmap>();
1296
1
    factory.register_function<FunctionBitmapSubsetLimit>();
1297
1
    factory.register_function<FunctionBitmapSubsetInRange>();
1298
1
    factory.register_function<FunctionBitmapToArray>();
1299
1
}
1300
1301
} // namespace doris