Coverage Report

Created: 2026-07-27 12:46

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
272
    static DataTypePtr get_return_type() { return std::make_shared<DataTypeBitMap>(); }
83
272
    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
1.10k
    static void vector(const ColumnType* col, MutableColumnPtr& col_res) {
92
1.10k
        execute<ColumnType, false>(col, nullptr, col_res);
93
1.10k
    }
_ZN5doris8ToBitmap6vectorINS_9ColumnStrIjEEEEvPKT_RNS_3COWINS_7IColumnEE11mutable_ptrIS8_EE
Line
Count
Source
91
12
    static void vector(const ColumnType* col, MutableColumnPtr& col_res) {
92
12
        execute<ColumnType, false>(col, nullptr, col_res);
93
12
    }
_ZN5doris8ToBitmap6vectorINS_12ColumnVectorILNS_13PrimitiveTypeE6EEEEEvPKT_RNS_3COWINS_7IColumnEE11mutable_ptrIS9_EE
Line
Count
Source
91
1.09k
    static void vector(const ColumnType* col, MutableColumnPtr& col_res) {
92
1.09k
        execute<ColumnType, false>(col, nullptr, col_res);
93
1.09k
    }
94
    template <typename ColumnType>
95
    static void vector_nullable(const ColumnType* col, const NullMap& nullmap,
96
566
                                MutableColumnPtr& col_res) {
97
566
        execute<ColumnType, true>(col, &nullmap, col_res);
98
566
    }
_ZN5doris8ToBitmap15vector_nullableINS_9ColumnStrIjEEEEvPKT_RKNS_8PODArrayIhLm4096ENS_9AllocatorILb0ELb0ELb0ENS_22DefaultMemoryAllocatorELb1EEELm16ELm15EEERNS_3COWINS_7IColumnEE11mutable_ptrISF_EE
Line
Count
Source
96
51
                                MutableColumnPtr& col_res) {
97
51
        execute<ColumnType, true>(col, &nullmap, col_res);
98
51
    }
_ZN5doris8ToBitmap15vector_nullableINS_12ColumnVectorILNS_13PrimitiveTypeE6EEEEEvPKT_RKNS_8PODArrayIhLm4096ENS_9AllocatorILb0ELb0ELb0ENS_22DefaultMemoryAllocatorELb1EEELm16ELm15EEERNS_3COWINS_7IColumnEE11mutable_ptrISG_EE
Line
Count
Source
96
515
                                MutableColumnPtr& col_res) {
97
515
        execute<ColumnType, true>(col, &nullmap, col_res);
98
515
    }
99
    template <typename ColumnType, bool arg_is_nullable>
100
1.67k
    static void execute(const ColumnType* col, const NullMap* nullmap, MutableColumnPtr& col_res) {
101
1.67k
        if constexpr (std::is_same_v<ColumnType, ColumnString>) {
102
63
            const ColumnString::Chars& data = col->get_chars();
103
63
            const ColumnString::Offsets& offsets = col->get_offsets();
104
105
63
            auto* res_column = reinterpret_cast<ColumnBitmap*>(col_res.get());
106
63
            auto& res_data = res_column->get_data();
107
63
            size_t size = offsets.size();
108
109
3.56k
            for (size_t i = 0; i < size; ++i) {
110
3.49k
                if (arg_is_nullable && ((*nullmap)[i])) {
111
26
                    continue;
112
3.47k
                } else {
113
3.47k
                    const char* raw_str = reinterpret_cast<const char*>(&data[offsets[i - 1]]);
114
3.47k
                    int str_size = cast_set<int>(offsets[i] - offsets[i - 1]);
115
3.47k
                    StringParser::ParseResult parse_result = StringParser::PARSE_SUCCESS;
116
3.47k
                    uint64_t int_value = StringParser::string_to_unsigned_int<uint64_t>(
117
3.47k
                            raw_str, str_size, &parse_result);
118
3.47k
                    if (LIKELY(parse_result == StringParser::PARSE_SUCCESS)) {
119
3.26k
                        res_data[i].add(int_value);
120
3.26k
                    }
121
3.47k
                }
122
3.49k
            }
123
1.60k
        } else if constexpr (std::is_same_v<ColumnType, ColumnInt64>) {
124
1.60k
            auto* res_column = reinterpret_cast<ColumnBitmap*>(col_res.get());
125
1.60k
            auto& res_data = res_column->get_data();
126
1.60k
            size_t size = col->size();
127
128
136k
            for (size_t i = 0; i < size; ++i) {
129
134k
                if constexpr (arg_is_nullable) {
130
2.23k
                    if ((*nullmap)[i]) {
131
1.11k
                        continue;
132
1.11k
                    }
133
2.23k
                }
134
134k
                if (auto value = col->get_data()[i]; value >= 0) {
135
132k
                    res_data[i].add(value);
136
132k
                }
137
134k
            }
138
1.60k
        }
139
1.67k
    }
_ZN5doris8ToBitmap7executeINS_9ColumnStrIjEELb1EEEvPKT_PKNS_8PODArrayIhLm4096ENS_9AllocatorILb0ELb0ELb0ENS_22DefaultMemoryAllocatorELb1EEELm16ELm15EEERNS_3COWINS_7IColumnEE11mutable_ptrISF_EE
Line
Count
Source
100
51
    static void execute(const ColumnType* col, const NullMap* nullmap, MutableColumnPtr& col_res) {
101
51
        if constexpr (std::is_same_v<ColumnType, ColumnString>) {
102
51
            const ColumnString::Chars& data = col->get_chars();
103
51
            const ColumnString::Offsets& offsets = col->get_offsets();
104
105
51
            auto* res_column = reinterpret_cast<ColumnBitmap*>(col_res.get());
106
51
            auto& res_data = res_column->get_data();
107
51
            size_t size = offsets.size();
108
109
3.52k
            for (size_t i = 0; i < size; ++i) {
110
3.47k
                if (arg_is_nullable && ((*nullmap)[i])) {
111
26
                    continue;
112
3.44k
                } else {
113
3.44k
                    const char* raw_str = reinterpret_cast<const char*>(&data[offsets[i - 1]]);
114
3.44k
                    int str_size = cast_set<int>(offsets[i] - offsets[i - 1]);
115
3.44k
                    StringParser::ParseResult parse_result = StringParser::PARSE_SUCCESS;
116
3.44k
                    uint64_t int_value = StringParser::string_to_unsigned_int<uint64_t>(
117
3.44k
                            raw_str, str_size, &parse_result);
118
3.44k
                    if (LIKELY(parse_result == StringParser::PARSE_SUCCESS)) {
119
3.26k
                        res_data[i].add(int_value);
120
3.26k
                    }
121
3.44k
                }
122
3.47k
            }
123
        } else if constexpr (std::is_same_v<ColumnType, ColumnInt64>) {
124
            auto* res_column = reinterpret_cast<ColumnBitmap*>(col_res.get());
125
            auto& res_data = res_column->get_data();
126
            size_t size = col->size();
127
128
            for (size_t i = 0; i < size; ++i) {
129
                if constexpr (arg_is_nullable) {
130
                    if ((*nullmap)[i]) {
131
                        continue;
132
                    }
133
                }
134
                if (auto value = col->get_data()[i]; value >= 0) {
135
                    res_data[i].add(value);
136
                }
137
            }
138
        }
139
51
    }
_ZN5doris8ToBitmap7executeINS_12ColumnVectorILNS_13PrimitiveTypeE6EEELb1EEEvPKT_PKNS_8PODArrayIhLm4096ENS_9AllocatorILb0ELb0ELb0ENS_22DefaultMemoryAllocatorELb1EEELm16ELm15EEERNS_3COWINS_7IColumnEE11mutable_ptrISG_EE
Line
Count
Source
100
513
    static void execute(const ColumnType* col, const NullMap* nullmap, MutableColumnPtr& col_res) {
101
        if constexpr (std::is_same_v<ColumnType, ColumnString>) {
102
            const ColumnString::Chars& data = col->get_chars();
103
            const ColumnString::Offsets& offsets = col->get_offsets();
104
105
            auto* res_column = reinterpret_cast<ColumnBitmap*>(col_res.get());
106
            auto& res_data = res_column->get_data();
107
            size_t size = offsets.size();
108
109
            for (size_t i = 0; i < size; ++i) {
110
                if (arg_is_nullable && ((*nullmap)[i])) {
111
                    continue;
112
                } else {
113
                    const char* raw_str = reinterpret_cast<const char*>(&data[offsets[i - 1]]);
114
                    int str_size = cast_set<int>(offsets[i] - offsets[i - 1]);
115
                    StringParser::ParseResult parse_result = StringParser::PARSE_SUCCESS;
116
                    uint64_t int_value = StringParser::string_to_unsigned_int<uint64_t>(
117
                            raw_str, str_size, &parse_result);
118
                    if (LIKELY(parse_result == StringParser::PARSE_SUCCESS)) {
119
                        res_data[i].add(int_value);
120
                    }
121
                }
122
            }
123
513
        } else if constexpr (std::is_same_v<ColumnType, ColumnInt64>) {
124
513
            auto* res_column = reinterpret_cast<ColumnBitmap*>(col_res.get());
125
513
            auto& res_data = res_column->get_data();
126
513
            size_t size = col->size();
127
128
3.85k
            for (size_t i = 0; i < size; ++i) {
129
2.23k
                if constexpr (arg_is_nullable) {
130
2.23k
                    if ((*nullmap)[i]) {
131
1.11k
                        continue;
132
1.11k
                    }
133
2.23k
                }
134
2.23k
                if (auto value = col->get_data()[i]; value >= 0) {
135
786
                    res_data[i].add(value);
136
786
                }
137
2.23k
            }
138
513
        }
139
513
    }
_ZN5doris8ToBitmap7executeINS_9ColumnStrIjEELb0EEEvPKT_PKNS_8PODArrayIhLm4096ENS_9AllocatorILb0ELb0ELb0ENS_22DefaultMemoryAllocatorELb1EEELm16ELm15EEERNS_3COWINS_7IColumnEE11mutable_ptrISF_EE
Line
Count
Source
100
12
    static void execute(const ColumnType* col, const NullMap* nullmap, MutableColumnPtr& col_res) {
101
12
        if constexpr (std::is_same_v<ColumnType, ColumnString>) {
102
12
            const ColumnString::Chars& data = col->get_chars();
103
12
            const ColumnString::Offsets& offsets = col->get_offsets();
104
105
12
            auto* res_column = reinterpret_cast<ColumnBitmap*>(col_res.get());
106
12
            auto& res_data = res_column->get_data();
107
12
            size_t size = offsets.size();
108
109
40
            for (size_t i = 0; i < size; ++i) {
110
28
                if (arg_is_nullable && ((*nullmap)[i])) {
111
0
                    continue;
112
28
                } else {
113
28
                    const char* raw_str = reinterpret_cast<const char*>(&data[offsets[i - 1]]);
114
28
                    int str_size = cast_set<int>(offsets[i] - offsets[i - 1]);
115
28
                    StringParser::ParseResult parse_result = StringParser::PARSE_SUCCESS;
116
28
                    uint64_t int_value = StringParser::string_to_unsigned_int<uint64_t>(
117
28
                            raw_str, str_size, &parse_result);
118
28
                    if (LIKELY(parse_result == StringParser::PARSE_SUCCESS)) {
119
0
                        res_data[i].add(int_value);
120
0
                    }
121
28
                }
122
28
            }
123
        } else if constexpr (std::is_same_v<ColumnType, ColumnInt64>) {
124
            auto* res_column = reinterpret_cast<ColumnBitmap*>(col_res.get());
125
            auto& res_data = res_column->get_data();
126
            size_t size = col->size();
127
128
            for (size_t i = 0; i < size; ++i) {
129
                if constexpr (arg_is_nullable) {
130
                    if ((*nullmap)[i]) {
131
                        continue;
132
                    }
133
                }
134
                if (auto value = col->get_data()[i]; value >= 0) {
135
                    res_data[i].add(value);
136
                }
137
            }
138
        }
139
12
    }
_ZN5doris8ToBitmap7executeINS_12ColumnVectorILNS_13PrimitiveTypeE6EEELb0EEEvPKT_PKNS_8PODArrayIhLm4096ENS_9AllocatorILb0ELb0ELb0ENS_22DefaultMemoryAllocatorELb1EEELm16ELm15EEERNS_3COWINS_7IColumnEE11mutable_ptrISG_EE
Line
Count
Source
100
1.09k
    static void execute(const ColumnType* col, const NullMap* nullmap, MutableColumnPtr& col_res) {
101
        if constexpr (std::is_same_v<ColumnType, ColumnString>) {
102
            const ColumnString::Chars& data = col->get_chars();
103
            const ColumnString::Offsets& offsets = col->get_offsets();
104
105
            auto* res_column = reinterpret_cast<ColumnBitmap*>(col_res.get());
106
            auto& res_data = res_column->get_data();
107
            size_t size = offsets.size();
108
109
            for (size_t i = 0; i < size; ++i) {
110
                if (arg_is_nullable && ((*nullmap)[i])) {
111
                    continue;
112
                } else {
113
                    const char* raw_str = reinterpret_cast<const char*>(&data[offsets[i - 1]]);
114
                    int str_size = cast_set<int>(offsets[i] - offsets[i - 1]);
115
                    StringParser::ParseResult parse_result = StringParser::PARSE_SUCCESS;
116
                    uint64_t int_value = StringParser::string_to_unsigned_int<uint64_t>(
117
                            raw_str, str_size, &parse_result);
118
                    if (LIKELY(parse_result == StringParser::PARSE_SUCCESS)) {
119
                        res_data[i].add(int_value);
120
                    }
121
                }
122
            }
123
1.09k
        } else if constexpr (std::is_same_v<ColumnType, ColumnInt64>) {
124
1.09k
            auto* res_column = reinterpret_cast<ColumnBitmap*>(col_res.get());
125
1.09k
            auto& res_data = res_column->get_data();
126
1.09k
            size_t size = col->size();
127
128
132k
            for (size_t i = 0; i < size; ++i) {
129
                if constexpr (arg_is_nullable) {
130
                    if ((*nullmap)[i]) {
131
                        continue;
132
                    }
133
                }
134
132k
                if (auto value = col->get_data()[i]; value >= 0) {
135
132k
                    res_data[i].add(value);
136
132k
                }
137
131k
            }
138
1.09k
        }
139
1.09k
    }
140
};
141
142
struct ToBitmapWithCheck {
143
    static constexpr auto name = "to_bitmap_with_check";
144
    using ReturnType = DataTypeBitMap;
145
146
    template <typename ColumnType>
147
52
    static Status vector(const ColumnType* col, MutableColumnPtr& col_res) {
148
52
        return execute<ColumnType, false>(col, nullptr, col_res);
149
52
    }
Unexecuted instantiation: _ZN5doris17ToBitmapWithCheck6vectorINS_9ColumnStrIjEEEENS_6StatusEPKT_RNS_3COWINS_7IColumnEE11mutable_ptrIS9_EE
_ZN5doris17ToBitmapWithCheck6vectorINS_12ColumnVectorILNS_13PrimitiveTypeE6EEEEENS_6StatusEPKT_RNS_3COWINS_7IColumnEE11mutable_ptrISA_EE
Line
Count
Source
147
52
    static Status vector(const ColumnType* col, MutableColumnPtr& col_res) {
148
52
        return execute<ColumnType, false>(col, nullptr, col_res);
149
52
    }
150
    template <typename ColumnType>
151
    static Status vector_nullable(const ColumnType* col, const NullMap& nullmap,
152
51
                                  MutableColumnPtr& col_res) {
153
51
        return execute<ColumnType, true>(col, &nullmap, col_res);
154
51
    }
Unexecuted instantiation: _ZN5doris17ToBitmapWithCheck15vector_nullableINS_9ColumnStrIjEEEENS_6StatusEPKT_RKNS_8PODArrayIhLm4096ENS_9AllocatorILb0ELb0ELb0ENS_22DefaultMemoryAllocatorELb1EEELm16ELm15EEERNS_3COWINS_7IColumnEE11mutable_ptrISG_EE
_ZN5doris17ToBitmapWithCheck15vector_nullableINS_12ColumnVectorILNS_13PrimitiveTypeE6EEEEENS_6StatusEPKT_RKNS_8PODArrayIhLm4096ENS_9AllocatorILb0ELb0ELb0ENS_22DefaultMemoryAllocatorELb1EEELm16ELm15EEERNS_3COWINS_7IColumnEE11mutable_ptrISH_EE
Line
Count
Source
152
51
                                  MutableColumnPtr& col_res) {
153
51
        return execute<ColumnType, true>(col, &nullmap, col_res);
154
51
    }
155
    template <typename ColumnType, bool arg_is_nullable>
156
    static Status execute(const ColumnType* col, const NullMap* nullmap,
157
103
                          MutableColumnPtr& col_res) {
158
103
        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
103
        } else if constexpr (std::is_same_v<ColumnType, ColumnInt64>) {
188
103
            auto* res_column = reinterpret_cast<ColumnBitmap*>(col_res.get());
189
103
            auto& res_data = res_column->get_data();
190
103
            size_t size = col->size();
191
192
230
            for (size_t i = 0; i < size; ++i) {
193
130
                if (arg_is_nullable && ((*nullmap)[i])) {
194
21
                    continue;
195
109
                } else {
196
109
                    int64_t int_value = col->get_data()[i];
197
109
                    if (LIKELY(int_value >= 0)) {
198
106
                        res_data[i].add(int_value);
199
106
                    } else {
200
3
                        return Status::InvalidArgument(
201
3
                                "The input: {} is not valid, to_bitmap only support bigint value "
202
3
                                "from 0 to 18446744073709551615 currently, cannot create MV with "
203
3
                                "to_bitmap on column with negative values or cannot load negative "
204
3
                                "values to column with to_bitmap MV on it.",
205
3
                                int_value);
206
3
                    }
207
109
                }
208
130
            }
209
        } else {
210
            return Status::InvalidArgument("not support type");
211
        }
212
100
        return Status::OK();
213
103
    }
Unexecuted instantiation: _ZN5doris17ToBitmapWithCheck7executeINS_9ColumnStrIjEELb1EEENS_6StatusEPKT_PKNS_8PODArrayIhLm4096ENS_9AllocatorILb0ELb0ELb0ENS_22DefaultMemoryAllocatorELb1EEELm16ELm15EEERNS_3COWINS_7IColumnEE11mutable_ptrISG_EE
_ZN5doris17ToBitmapWithCheck7executeINS_12ColumnVectorILNS_13PrimitiveTypeE6EEELb1EEENS_6StatusEPKT_PKNS_8PODArrayIhLm4096ENS_9AllocatorILb0ELb0ELb0ENS_22DefaultMemoryAllocatorELb1EEELm16ELm15EEERNS_3COWINS_7IColumnEE11mutable_ptrISH_EE
Line
Count
Source
157
51
                          MutableColumnPtr& col_res) {
158
        if constexpr (std::is_same_v<ColumnType, ColumnString>) {
159
            const ColumnString::Chars& data = col->get_chars();
160
            const ColumnString::Offsets& offsets = col->get_offsets();
161
            auto* res_column = reinterpret_cast<ColumnBitmap*>(col_res.get());
162
            auto& res_data = res_column->get_data();
163
            size_t size = offsets.size();
164
165
            for (size_t i = 0; i < size; ++i) {
166
                if (arg_is_nullable && ((*nullmap)[i])) {
167
                    continue;
168
                } else {
169
                    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
                    int str_size = cast_set<int>(offsets[i] - offsets[i - 1]);
172
                    StringParser::ParseResult parse_result = StringParser::PARSE_SUCCESS;
173
                    uint64_t int_value = StringParser::string_to_unsigned_int<uint64_t>(
174
                            raw_str, str_size, &parse_result);
175
                    if (LIKELY(parse_result == StringParser::PARSE_SUCCESS)) {
176
                        res_data[i].add(int_value);
177
                    } else {
178
                        return Status::InvalidArgument(
179
                                "The input: {} is not valid, to_bitmap only support bigint value "
180
                                "from 0 to 18446744073709551615 currently, cannot create MV with "
181
                                "to_bitmap on column with negative values or cannot load negative "
182
                                "values to column with to_bitmap MV on it.",
183
                                std::string(raw_str, str_size));
184
                    }
185
                }
186
            }
187
51
        } else if constexpr (std::is_same_v<ColumnType, ColumnInt64>) {
188
51
            auto* res_column = reinterpret_cast<ColumnBitmap*>(col_res.get());
189
51
            auto& res_data = res_column->get_data();
190
51
            size_t size = col->size();
191
192
121
            for (size_t i = 0; i < size; ++i) {
193
70
                if (arg_is_nullable && ((*nullmap)[i])) {
194
21
                    continue;
195
49
                } else {
196
49
                    int64_t int_value = col->get_data()[i];
197
49
                    if (LIKELY(int_value >= 0)) {
198
49
                        res_data[i].add(int_value);
199
49
                    } 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
49
                }
208
70
            }
209
        } else {
210
            return Status::InvalidArgument("not support type");
211
        }
212
51
        return Status::OK();
213
51
    }
Unexecuted instantiation: _ZN5doris17ToBitmapWithCheck7executeINS_9ColumnStrIjEELb0EEENS_6StatusEPKT_PKNS_8PODArrayIhLm4096ENS_9AllocatorILb0ELb0ELb0ENS_22DefaultMemoryAllocatorELb1EEELm16ELm15EEERNS_3COWINS_7IColumnEE11mutable_ptrISG_EE
_ZN5doris17ToBitmapWithCheck7executeINS_12ColumnVectorILNS_13PrimitiveTypeE6EEELb0EEENS_6StatusEPKT_PKNS_8PODArrayIhLm4096ENS_9AllocatorILb0ELb0ELb0ENS_22DefaultMemoryAllocatorELb1EEELm16ELm15EEERNS_3COWINS_7IColumnEE11mutable_ptrISH_EE
Line
Count
Source
157
52
                          MutableColumnPtr& col_res) {
158
        if constexpr (std::is_same_v<ColumnType, ColumnString>) {
159
            const ColumnString::Chars& data = col->get_chars();
160
            const ColumnString::Offsets& offsets = col->get_offsets();
161
            auto* res_column = reinterpret_cast<ColumnBitmap*>(col_res.get());
162
            auto& res_data = res_column->get_data();
163
            size_t size = offsets.size();
164
165
            for (size_t i = 0; i < size; ++i) {
166
                if (arg_is_nullable && ((*nullmap)[i])) {
167
                    continue;
168
                } else {
169
                    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
                    int str_size = cast_set<int>(offsets[i] - offsets[i - 1]);
172
                    StringParser::ParseResult parse_result = StringParser::PARSE_SUCCESS;
173
                    uint64_t int_value = StringParser::string_to_unsigned_int<uint64_t>(
174
                            raw_str, str_size, &parse_result);
175
                    if (LIKELY(parse_result == StringParser::PARSE_SUCCESS)) {
176
                        res_data[i].add(int_value);
177
                    } else {
178
                        return Status::InvalidArgument(
179
                                "The input: {} is not valid, to_bitmap only support bigint value "
180
                                "from 0 to 18446744073709551615 currently, cannot create MV with "
181
                                "to_bitmap on column with negative values or cannot load negative "
182
                                "values to column with to_bitmap MV on it.",
183
                                std::string(raw_str, str_size));
184
                    }
185
                }
186
            }
187
52
        } else if constexpr (std::is_same_v<ColumnType, ColumnInt64>) {
188
52
            auto* res_column = reinterpret_cast<ColumnBitmap*>(col_res.get());
189
52
            auto& res_data = res_column->get_data();
190
52
            size_t size = col->size();
191
192
109
            for (size_t i = 0; i < size; ++i) {
193
60
                if (arg_is_nullable && ((*nullmap)[i])) {
194
0
                    continue;
195
60
                } else {
196
60
                    int64_t int_value = col->get_data()[i];
197
60
                    if (LIKELY(int_value >= 0)) {
198
57
                        res_data[i].add(int_value);
199
57
                    } else {
200
3
                        return Status::InvalidArgument(
201
3
                                "The input: {} is not valid, to_bitmap only support bigint value "
202
3
                                "from 0 to 18446744073709551615 currently, cannot create MV with "
203
3
                                "to_bitmap on column with negative values or cannot load negative "
204
3
                                "values to column with to_bitmap MV on it.",
205
3
                                int_value);
206
3
                    }
207
60
                }
208
60
            }
209
        } else {
210
            return Status::InvalidArgument("not support type");
211
        }
212
49
        return Status::OK();
213
52
    }
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
311
                         size_t input_rows_count) {
224
311
        res.reserve(input_rows_count);
225
311
        std::vector<uint64_t> bits;
226
311
        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
400
        auto split_and_parse = [&bits](const char* raw_str, size_t str_size) {
234
400
            bits.clear();
235
400
            auto res = absl::StrSplit(std::string_view {raw_str, str_size}, ",", absl::SkipEmpty());
236
400
            uint64_t value = 0;
237
1.86k
            for (auto s : res) {
238
1.86k
                if (!absl::SimpleAtoi(s, &value)) {
239
66
                    return false;
240
66
                }
241
1.79k
                bits.push_back(value);
242
1.79k
            }
243
334
            return true;
244
400
        };
245
246
        // split by comma
247
248
711
        for (size_t i = 0; i < input_rows_count; ++i) {
249
400
            const char* raw_str = reinterpret_cast<const char*>(&data[offsets[i - 1]]);
250
400
            int64_t str_size = offsets[i] - offsets[i - 1];
251
252
400
            if ((str_size > INT32_MAX) || !split_and_parse(raw_str, str_size)) {
253
66
                res.emplace_back();
254
66
                null_map[i] = 1;
255
66
                continue;
256
66
            }
257
334
            res.emplace_back(bits);
258
334
        }
259
311
        return Status::OK();
260
311
    }
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
25
                         size_t input_rows_count) {
274
25
        res.reserve(input_rows_count);
275
25
        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
25
        std::string decode_buff;
282
25
        size_t last_decode_buff_len = 0;
283
25
        size_t curr_decode_buff_len = 0;
284
73
        for (size_t i = 0; i < input_rows_count; ++i) {
285
49
            const char* src_str = reinterpret_cast<const char*>(&data[offsets[i - 1]]);
286
49
            size_t src_size = offsets[i] - offsets[i - 1];
287
49
            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
49
            curr_decode_buff_len = src_size + 3;
295
49
            if (curr_decode_buff_len > last_decode_buff_len) {
296
35
                decode_buff.resize(curr_decode_buff_len);
297
35
                last_decode_buff_len = curr_decode_buff_len;
298
35
            }
299
49
            auto outlen = base64_decode(src_str, src_size, decode_buff.data());
300
49
            if (outlen < 0) {
301
0
                res.emplace_back();
302
0
                null_map[i] = 1;
303
49
            } else {
304
49
                BitmapValue bitmap_val;
305
49
                if (!bitmap_val.deserialize(decode_buff.data())) {
306
1
                    return Status::RuntimeError("bitmap_from_base64 decode failed: base64: {}",
307
1
                                                std::string(src_str, src_size));
308
1
                }
309
48
                res.emplace_back(std::move(bitmap_val));
310
48
            }
311
49
        }
312
24
        return Status::OK();
313
25
    }
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
19
                         std::vector<BitmapValue>& res, NullMap& null_map) {
323
19
        const auto& nested_column_data = static_cast<const ColumnType&>(nested_column).get_data();
324
19
        auto size = offset_column_data.size();
325
19
        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
19
        using ValueType = typename ColumnType::value_type;
330
19
        std::vector<ValueType> bits;
331
48
        for (size_t i = 0; i < size; ++i) {
332
29
            auto curr_offset = offset_column_data[i];
333
29
            auto prev_offset = offset_column_data[i - 1];
334
29
            bits.reserve(curr_offset - prev_offset);
335
134
            for (auto j = prev_offset; j < curr_offset; ++j) {
336
107
                auto data = nested_column_data[j];
337
                // invaild value
338
107
                if (UNLIKELY(data < 0) || UNLIKELY(nested_null_map[j])) {
339
2
                    res.emplace_back();
340
2
                    null_map[i] = 1;
341
2
                    break;
342
105
                } else {
343
105
                    bits.push_back(data);
344
105
                }
345
107
            }
346
            //input is valid value
347
29
            if (!null_map[i]) {
348
27
                res.emplace_back(bits);
349
27
            }
350
29
            bits.clear();
351
29
        }
352
19
        return Status::OK();
353
19
    }
_ZN5doris15BitmapFromArray6vectorINS_12ColumnVectorILNS_13PrimitiveTypeE3EEEEENS_6StatusERKNS_8PODArrayImLm4096ENS_9AllocatorILb0ELb0ELb0ENS_22DefaultMemoryAllocatorELb1EEELm16ELm15EEERKNS_7IColumnERKNS6_IhLm4096ES9_Lm16ELm15EEERSt6vectorINS_11BitmapValueESaISK_EERSG_
Line
Count
Source
322
3
                         std::vector<BitmapValue>& res, NullMap& null_map) {
323
3
        const auto& nested_column_data = static_cast<const ColumnType&>(nested_column).get_data();
324
3
        auto size = offset_column_data.size();
325
3
        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
3
        using ValueType = typename ColumnType::value_type;
330
3
        std::vector<ValueType> bits;
331
6
        for (size_t i = 0; i < size; ++i) {
332
3
            auto curr_offset = offset_column_data[i];
333
3
            auto prev_offset = offset_column_data[i - 1];
334
3
            bits.reserve(curr_offset - prev_offset);
335
16
            for (auto j = prev_offset; j < curr_offset; ++j) {
336
13
                auto data = nested_column_data[j];
337
                // invaild value
338
13
                if (UNLIKELY(data < 0) || UNLIKELY(nested_null_map[j])) {
339
0
                    res.emplace_back();
340
0
                    null_map[i] = 1;
341
0
                    break;
342
13
                } else {
343
13
                    bits.push_back(data);
344
13
                }
345
13
            }
346
            //input is valid value
347
3
            if (!null_map[i]) {
348
3
                res.emplace_back(bits);
349
3
            }
350
3
            bits.clear();
351
3
        }
352
3
        return Status::OK();
353
3
    }
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_
_ZN5doris15BitmapFromArray6vectorINS_12ColumnVectorILNS_13PrimitiveTypeE5EEEEENS_6StatusERKNS_8PODArrayImLm4096ENS_9AllocatorILb0ELb0ELb0ENS_22DefaultMemoryAllocatorELb1EEELm16ELm15EEERKNS_7IColumnERKNS6_IhLm4096ES9_Lm16ELm15EEERSt6vectorINS_11BitmapValueESaISK_EERSG_
Line
Count
Source
322
9
                         std::vector<BitmapValue>& res, NullMap& null_map) {
323
9
        const auto& nested_column_data = static_cast<const ColumnType&>(nested_column).get_data();
324
9
        auto size = offset_column_data.size();
325
9
        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
9
        using ValueType = typename ColumnType::value_type;
330
9
        std::vector<ValueType> bits;
331
26
        for (size_t i = 0; i < size; ++i) {
332
17
            auto curr_offset = offset_column_data[i];
333
17
            auto prev_offset = offset_column_data[i - 1];
334
17
            bits.reserve(curr_offset - prev_offset);
335
98
            for (auto j = prev_offset; j < curr_offset; ++j) {
336
83
                auto data = nested_column_data[j];
337
                // invaild value
338
83
                if (UNLIKELY(data < 0) || UNLIKELY(nested_null_map[j])) {
339
2
                    res.emplace_back();
340
2
                    null_map[i] = 1;
341
2
                    break;
342
81
                } else {
343
81
                    bits.push_back(data);
344
81
                }
345
83
            }
346
            //input is valid value
347
17
            if (!null_map[i]) {
348
15
                res.emplace_back(bits);
349
15
            }
350
17
            bits.clear();
351
17
        }
352
9
        return Status::OK();
353
9
    }
_ZN5doris15BitmapFromArray6vectorINS_12ColumnVectorILNS_13PrimitiveTypeE6EEEEENS_6StatusERKNS_8PODArrayImLm4096ENS_9AllocatorILb0ELb0ELb0ENS_22DefaultMemoryAllocatorELb1EEELm16ELm15EEERKNS_7IColumnERKNS6_IhLm4096ES9_Lm16ELm15EEERSt6vectorINS_11BitmapValueESaISK_EERSG_
Line
Count
Source
322
7
                         std::vector<BitmapValue>& res, NullMap& null_map) {
323
7
        const auto& nested_column_data = static_cast<const ColumnType&>(nested_column).get_data();
324
7
        auto size = offset_column_data.size();
325
7
        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
7
        using ValueType = typename ColumnType::value_type;
330
7
        std::vector<ValueType> bits;
331
16
        for (size_t i = 0; i < size; ++i) {
332
9
            auto curr_offset = offset_column_data[i];
333
9
            auto prev_offset = offset_column_data[i - 1];
334
9
            bits.reserve(curr_offset - prev_offset);
335
20
            for (auto j = prev_offset; j < curr_offset; ++j) {
336
11
                auto data = nested_column_data[j];
337
                // invaild value
338
11
                if (UNLIKELY(data < 0) || UNLIKELY(nested_null_map[j])) {
339
0
                    res.emplace_back();
340
0
                    null_map[i] = 1;
341
0
                    break;
342
11
                } else {
343
11
                    bits.push_back(data);
344
11
                }
345
11
            }
346
            //input is valid value
347
9
            if (!null_map[i]) {
348
9
                res.emplace_back(bits);
349
9
            }
350
9
            bits.clear();
351
9
        }
352
7
        return Status::OK();
353
7
    }
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
368
    static FunctionPtr create() { return std::make_shared<FunctionBitmapAlwaysNull>(); }
_ZN5doris24FunctionBitmapAlwaysNullINS_16BitmapFromStringEE6createEv
Line
Count
Source
363
306
    static FunctionPtr create() { return std::make_shared<FunctionBitmapAlwaysNull>(); }
_ZN5doris24FunctionBitmapAlwaysNullINS_16BitmapFromBase64EE6createEv
Line
Count
Source
363
33
    static FunctionPtr create() { return std::make_shared<FunctionBitmapAlwaysNull>(); }
_ZN5doris24FunctionBitmapAlwaysNullINS_15BitmapFromArrayEE6createEv
Line
Count
Source
363
29
    static FunctionPtr create() { return std::make_shared<FunctionBitmapAlwaysNull>(); }
364
365
341
    DataTypePtr get_return_type_impl(const DataTypes& arguments) const override {
366
341
        return make_nullable(std::make_shared<DataTypeBitMap>());
367
341
    }
_ZNK5doris24FunctionBitmapAlwaysNullINS_16BitmapFromStringEE20get_return_type_implERKSt6vectorISt10shared_ptrIKNS_9IDataTypeEESaIS7_EE
Line
Count
Source
365
297
    DataTypePtr get_return_type_impl(const DataTypes& arguments) const override {
366
297
        return make_nullable(std::make_shared<DataTypeBitMap>());
367
297
    }
_ZNK5doris24FunctionBitmapAlwaysNullINS_16BitmapFromBase64EE20get_return_type_implERKSt6vectorISt10shared_ptrIKNS_9IDataTypeEESaIS7_EE
Line
Count
Source
365
24
    DataTypePtr get_return_type_impl(const DataTypes& arguments) const override {
366
24
        return make_nullable(std::make_shared<DataTypeBitMap>());
367
24
    }
_ZNK5doris24FunctionBitmapAlwaysNullINS_15BitmapFromArrayEE20get_return_type_implERKSt6vectorISt10shared_ptrIKNS_9IDataTypeEESaIS7_EE
Line
Count
Source
365
20
    DataTypePtr get_return_type_impl(const DataTypes& arguments) const override {
366
20
        return make_nullable(std::make_shared<DataTypeBitMap>());
367
20
    }
368
369
341
    size_t get_number_of_arguments() const override { return 1; }
_ZNK5doris24FunctionBitmapAlwaysNullINS_16BitmapFromStringEE23get_number_of_argumentsEv
Line
Count
Source
369
297
    size_t get_number_of_arguments() const override { return 1; }
_ZNK5doris24FunctionBitmapAlwaysNullINS_16BitmapFromBase64EE23get_number_of_argumentsEv
Line
Count
Source
369
24
    size_t get_number_of_arguments() const override { return 1; }
_ZNK5doris24FunctionBitmapAlwaysNullINS_15BitmapFromArrayEE23get_number_of_argumentsEv
Line
Count
Source
369
20
    size_t get_number_of_arguments() const override { return 1; }
370
371
    Status execute_impl(FunctionContext* context, Block& block, const ColumnNumbers& arguments,
372
355
                        uint32_t result, size_t input_rows_count) const override {
373
355
        auto res_null_map = ColumnUInt8::create(input_rows_count, 0);
374
355
        auto res_data_column = ColumnBitmap::create();
375
355
        auto& null_map = res_null_map->get_data();
376
355
        auto& res = res_data_column->get_data();
377
378
355
        ColumnPtr& argument_column = block.get_by_position(arguments[0]).column;
379
355
        if constexpr (std::is_same_v<typename Impl::ArgumentType, DataTypeString>) {
380
336
            const auto& str_column = static_cast<const ColumnString&>(*argument_column);
381
336
            const ColumnString::Chars& data = str_column.get_chars();
382
336
            const ColumnString::Offsets& offsets = str_column.get_offsets();
383
336
            RETURN_IF_ERROR(Impl::vector(data, offsets, res, null_map, input_rows_count));
384
336
        } else if constexpr (std::is_same_v<typename Impl::ArgumentType, DataTypeArray>) {
385
19
            auto argument_type = remove_nullable(
386
19
                    assert_cast<const DataTypeArray&>(*block.get_by_position(arguments[0]).type)
387
19
                            .get_nested_type());
388
19
            const auto& array_column = static_cast<const ColumnArray&>(*argument_column);
389
19
            const auto& offset_column_data = array_column.get_offsets();
390
19
            const auto& nested_nullable_column =
391
19
                    static_cast<const ColumnNullable&>(array_column.get_data());
392
19
            const auto& nested_column = nested_nullable_column.get_nested_column();
393
19
            const auto& nested_null_map = nested_nullable_column.get_null_map_column().get_data();
394
395
19
            switch (argument_type->get_primitive_type()) {
396
3
            case PrimitiveType::TYPE_TINYINT:
397
3
                RETURN_IF_ERROR(Impl::template vector<ColumnInt8>(offset_column_data, nested_column,
398
3
                                                                  nested_null_map, res, null_map));
399
3
                break;
400
3
            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
9
            case PrimitiveType::TYPE_INT:
409
9
                RETURN_IF_ERROR(Impl::template vector<ColumnInt32>(
410
9
                        offset_column_data, nested_column, nested_null_map, res, null_map));
411
9
                break;
412
9
            case PrimitiveType::TYPE_BIGINT:
413
7
                RETURN_IF_ERROR(Impl::template vector<ColumnInt64>(
414
7
                        offset_column_data, nested_column, nested_null_map, res, null_map));
415
7
                break;
416
7
            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
19
            }
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
354
        block.get_by_position(result).column =
427
355
                ColumnNullable::create(std::move(res_data_column), std::move(res_null_map));
428
355
        return Status::OK();
429
355
    }
_ZNK5doris24FunctionBitmapAlwaysNullINS_16BitmapFromStringEE12execute_implEPNS_15FunctionContextERNS_5BlockERKSt6vectorIjSaIjEEjm
Line
Count
Source
372
311
                        uint32_t result, size_t input_rows_count) const override {
373
311
        auto res_null_map = ColumnUInt8::create(input_rows_count, 0);
374
311
        auto res_data_column = ColumnBitmap::create();
375
311
        auto& null_map = res_null_map->get_data();
376
311
        auto& res = res_data_column->get_data();
377
378
311
        ColumnPtr& argument_column = block.get_by_position(arguments[0]).column;
379
311
        if constexpr (std::is_same_v<typename Impl::ArgumentType, DataTypeString>) {
380
311
            const auto& str_column = static_cast<const ColumnString&>(*argument_column);
381
311
            const ColumnString::Chars& data = str_column.get_chars();
382
311
            const ColumnString::Offsets& offsets = str_column.get_offsets();
383
311
            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
311
        block.get_by_position(result).column =
427
311
                ColumnNullable::create(std::move(res_data_column), std::move(res_null_map));
428
311
        return Status::OK();
429
311
    }
_ZNK5doris24FunctionBitmapAlwaysNullINS_16BitmapFromBase64EE12execute_implEPNS_15FunctionContextERNS_5BlockERKSt6vectorIjSaIjEEjm
Line
Count
Source
372
25
                        uint32_t result, size_t input_rows_count) const override {
373
25
        auto res_null_map = ColumnUInt8::create(input_rows_count, 0);
374
25
        auto res_data_column = ColumnBitmap::create();
375
25
        auto& null_map = res_null_map->get_data();
376
25
        auto& res = res_data_column->get_data();
377
378
25
        ColumnPtr& argument_column = block.get_by_position(arguments[0]).column;
379
25
        if constexpr (std::is_same_v<typename Impl::ArgumentType, DataTypeString>) {
380
25
            const auto& str_column = static_cast<const ColumnString&>(*argument_column);
381
25
            const ColumnString::Chars& data = str_column.get_chars();
382
25
            const ColumnString::Offsets& offsets = str_column.get_offsets();
383
25
            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
24
        block.get_by_position(result).column =
427
25
                ColumnNullable::create(std::move(res_data_column), std::move(res_null_map));
428
25
        return Status::OK();
429
25
    }
_ZNK5doris24FunctionBitmapAlwaysNullINS_15BitmapFromArrayEE12execute_implEPNS_15FunctionContextERNS_5BlockERKSt6vectorIjSaIjEEjm
Line
Count
Source
372
19
                        uint32_t result, size_t input_rows_count) const override {
373
19
        auto res_null_map = ColumnUInt8::create(input_rows_count, 0);
374
19
        auto res_data_column = ColumnBitmap::create();
375
19
        auto& null_map = res_null_map->get_data();
376
19
        auto& res = res_data_column->get_data();
377
378
19
        ColumnPtr& argument_column = block.get_by_position(arguments[0]).column;
379
        if constexpr (std::is_same_v<typename Impl::ArgumentType, DataTypeString>) {
380
            const auto& str_column = static_cast<const ColumnString&>(*argument_column);
381
            const ColumnString::Chars& data = str_column.get_chars();
382
            const ColumnString::Offsets& offsets = str_column.get_offsets();
383
            RETURN_IF_ERROR(Impl::vector(data, offsets, res, null_map, input_rows_count));
384
19
        } else if constexpr (std::is_same_v<typename Impl::ArgumentType, DataTypeArray>) {
385
19
            auto argument_type = remove_nullable(
386
19
                    assert_cast<const DataTypeArray&>(*block.get_by_position(arguments[0]).type)
387
19
                            .get_nested_type());
388
19
            const auto& array_column = static_cast<const ColumnArray&>(*argument_column);
389
19
            const auto& offset_column_data = array_column.get_offsets();
390
19
            const auto& nested_nullable_column =
391
19
                    static_cast<const ColumnNullable&>(array_column.get_data());
392
19
            const auto& nested_column = nested_nullable_column.get_nested_column();
393
19
            const auto& nested_null_map = nested_nullable_column.get_null_map_column().get_data();
394
395
19
            switch (argument_type->get_primitive_type()) {
396
3
            case PrimitiveType::TYPE_TINYINT:
397
3
                RETURN_IF_ERROR(Impl::template vector<ColumnInt8>(offset_column_data, nested_column,
398
3
                                                                  nested_null_map, res, null_map));
399
3
                break;
400
3
            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
9
            case PrimitiveType::TYPE_INT:
409
9
                RETURN_IF_ERROR(Impl::template vector<ColumnInt32>(
410
9
                        offset_column_data, nested_column, nested_null_map, res, null_map));
411
9
                break;
412
9
            case PrimitiveType::TYPE_BIGINT:
413
7
                RETURN_IF_ERROR(Impl::template vector<ColumnInt64>(
414
7
                        offset_column_data, nested_column, nested_null_map, res, null_map));
415
7
                break;
416
7
            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
19
            }
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
19
        block.get_by_position(result).column =
427
19
                ColumnNullable::create(std::move(res_data_column), std::move(res_null_map));
428
19
        return Status::OK();
429
19
    }
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
130
    static void vector(const ColumnType* col, MutableColumnPtr& col_res) {
453
130
        if constexpr (std::is_same_v<ColumnType, ColumnString>) {
454
130
            const ColumnString::Chars& data = col->get_chars();
455
130
            const ColumnString::Offsets& offsets = col->get_offsets();
456
130
            auto* res_column = reinterpret_cast<ColumnBitmap*>(col_res.get());
457
130
            auto& res_data = res_column->get_data();
458
130
            size_t size = offsets.size();
459
460
436
            for (size_t i = 0; i < size; ++i) {
461
306
                const char* raw_str = reinterpret_cast<const char*>(&data[offsets[i - 1]]);
462
306
                size_t str_size = offsets[i] - offsets[i - 1];
463
306
                if constexpr (HashBits == 32) {
464
274
                    uint32_t hash_value =
465
274
                            HashUtil::murmur_hash3_32(raw_str, str_size, HashUtil::MURMUR3_32_SEED);
466
274
                    res_data[i].add(hash_value);
467
274
                } else {
468
32
                    uint64_t hash_value = 0;
469
32
                    murmur_hash3_x64_64(raw_str, str_size, 0, &hash_value);
470
32
                    res_data[i].add(hash_value);
471
32
                }
472
306
            }
473
130
        }
474
130
    }
_ZN5doris10BitmapHashILi32EE6vectorINS_9ColumnStrIjEEEEvPKT_RNS_3COWINS_7IColumnEE11mutable_ptrIS9_EE
Line
Count
Source
452
114
    static void vector(const ColumnType* col, MutableColumnPtr& col_res) {
453
114
        if constexpr (std::is_same_v<ColumnType, ColumnString>) {
454
114
            const ColumnString::Chars& data = col->get_chars();
455
114
            const ColumnString::Offsets& offsets = col->get_offsets();
456
114
            auto* res_column = reinterpret_cast<ColumnBitmap*>(col_res.get());
457
114
            auto& res_data = res_column->get_data();
458
114
            size_t size = offsets.size();
459
460
388
            for (size_t i = 0; i < size; ++i) {
461
274
                const char* raw_str = reinterpret_cast<const char*>(&data[offsets[i - 1]]);
462
274
                size_t str_size = offsets[i] - offsets[i - 1];
463
274
                if constexpr (HashBits == 32) {
464
274
                    uint32_t hash_value =
465
274
                            HashUtil::murmur_hash3_32(raw_str, str_size, HashUtil::MURMUR3_32_SEED);
466
274
                    res_data[i].add(hash_value);
467
                } else {
468
                    uint64_t hash_value = 0;
469
                    murmur_hash3_x64_64(raw_str, str_size, 0, &hash_value);
470
                    res_data[i].add(hash_value);
471
                }
472
274
            }
473
114
        }
474
114
    }
Unexecuted instantiation: _ZN5doris10BitmapHashILi32EE6vectorINS_12ColumnVectorILNS_13PrimitiveTypeE6EEEEEvPKT_RNS_3COWINS_7IColumnEE11mutable_ptrISA_EE
_ZN5doris10BitmapHashILi64EE6vectorINS_9ColumnStrIjEEEEvPKT_RNS_3COWINS_7IColumnEE11mutable_ptrIS9_EE
Line
Count
Source
452
16
    static void vector(const ColumnType* col, MutableColumnPtr& col_res) {
453
16
        if constexpr (std::is_same_v<ColumnType, ColumnString>) {
454
16
            const ColumnString::Chars& data = col->get_chars();
455
16
            const ColumnString::Offsets& offsets = col->get_offsets();
456
16
            auto* res_column = reinterpret_cast<ColumnBitmap*>(col_res.get());
457
16
            auto& res_data = res_column->get_data();
458
16
            size_t size = offsets.size();
459
460
48
            for (size_t i = 0; i < size; ++i) {
461
32
                const char* raw_str = reinterpret_cast<const char*>(&data[offsets[i - 1]]);
462
32
                size_t str_size = offsets[i] - offsets[i - 1];
463
                if constexpr (HashBits == 32) {
464
                    uint32_t hash_value =
465
                            HashUtil::murmur_hash3_32(raw_str, str_size, HashUtil::MURMUR3_32_SEED);
466
                    res_data[i].add(hash_value);
467
32
                } else {
468
32
                    uint64_t hash_value = 0;
469
32
                    murmur_hash3_x64_64(raw_str, str_size, 0, &hash_value);
470
32
                    res_data[i].add(hash_value);
471
32
                }
472
32
            }
473
16
        }
474
16
    }
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
198
                                MutableColumnPtr& col_res) {
479
198
        if constexpr (std::is_same_v<ColumnType, ColumnString>) {
480
198
            const ColumnString::Chars& data = col->get_chars();
481
198
            const ColumnString::Offsets& offsets = col->get_offsets();
482
198
            auto* res_column = reinterpret_cast<ColumnBitmap*>(col_res.get());
483
198
            auto& res_data = res_column->get_data();
484
198
            size_t size = offsets.size();
485
486
998
            for (size_t i = 0; i < size; ++i) {
487
800
                if (nullmap[i]) {
488
57
                    continue;
489
743
                } else {
490
743
                    const char* raw_str = reinterpret_cast<const char*>(&data[offsets[i - 1]]);
491
743
                    size_t str_size = offsets[i] - offsets[i - 1];
492
743
                    if constexpr (HashBits == 32) {
493
717
                        uint32_t hash_value = HashUtil::murmur_hash3_32(raw_str, str_size,
494
717
                                                                        HashUtil::MURMUR3_32_SEED);
495
717
                        res_data[i].add(hash_value);
496
717
                    } else {
497
26
                        uint64_t hash_value = 0;
498
26
                        murmur_hash3_x64_64(raw_str, str_size, 0, &hash_value);
499
26
                        res_data[i].add(hash_value);
500
26
                    }
501
743
                }
502
800
            }
503
198
        }
504
198
    }
_ZN5doris10BitmapHashILi32EE15vector_nullableINS_9ColumnStrIjEEEEvPKT_RKNS_8PODArrayIhLm4096ENS_9AllocatorILb0ELb0ELb0ENS_22DefaultMemoryAllocatorELb1EEELm16ELm15EEERNS_3COWINS_7IColumnEE11mutable_ptrISG_EE
Line
Count
Source
478
189
                                MutableColumnPtr& col_res) {
479
189
        if constexpr (std::is_same_v<ColumnType, ColumnString>) {
480
189
            const ColumnString::Chars& data = col->get_chars();
481
189
            const ColumnString::Offsets& offsets = col->get_offsets();
482
189
            auto* res_column = reinterpret_cast<ColumnBitmap*>(col_res.get());
483
189
            auto& res_data = res_column->get_data();
484
189
            size_t size = offsets.size();
485
486
962
            for (size_t i = 0; i < size; ++i) {
487
773
                if (nullmap[i]) {
488
56
                    continue;
489
717
                } else {
490
717
                    const char* raw_str = reinterpret_cast<const char*>(&data[offsets[i - 1]]);
491
717
                    size_t str_size = offsets[i] - offsets[i - 1];
492
717
                    if constexpr (HashBits == 32) {
493
717
                        uint32_t hash_value = HashUtil::murmur_hash3_32(raw_str, str_size,
494
717
                                                                        HashUtil::MURMUR3_32_SEED);
495
717
                        res_data[i].add(hash_value);
496
                    } else {
497
                        uint64_t hash_value = 0;
498
                        murmur_hash3_x64_64(raw_str, str_size, 0, &hash_value);
499
                        res_data[i].add(hash_value);
500
                    }
501
717
                }
502
773
            }
503
189
        }
504
189
    }
Unexecuted instantiation: _ZN5doris10BitmapHashILi32EE15vector_nullableINS_12ColumnVectorILNS_13PrimitiveTypeE6EEEEEvPKT_RKNS_8PODArrayIhLm4096ENS_9AllocatorILb0ELb0ELb0ENS_22DefaultMemoryAllocatorELb1EEELm16ELm15EEERNS_3COWINS_7IColumnEE11mutable_ptrISH_EE
_ZN5doris10BitmapHashILi64EE15vector_nullableINS_9ColumnStrIjEEEEvPKT_RKNS_8PODArrayIhLm4096ENS_9AllocatorILb0ELb0ELb0ENS_22DefaultMemoryAllocatorELb1EEELm16ELm15EEERNS_3COWINS_7IColumnEE11mutable_ptrISG_EE
Line
Count
Source
478
9
                                MutableColumnPtr& col_res) {
479
9
        if constexpr (std::is_same_v<ColumnType, ColumnString>) {
480
9
            const ColumnString::Chars& data = col->get_chars();
481
9
            const ColumnString::Offsets& offsets = col->get_offsets();
482
9
            auto* res_column = reinterpret_cast<ColumnBitmap*>(col_res.get());
483
9
            auto& res_data = res_column->get_data();
484
9
            size_t size = offsets.size();
485
486
36
            for (size_t i = 0; i < size; ++i) {
487
27
                if (nullmap[i]) {
488
1
                    continue;
489
26
                } else {
490
26
                    const char* raw_str = reinterpret_cast<const char*>(&data[offsets[i - 1]]);
491
26
                    size_t str_size = offsets[i] - offsets[i - 1];
492
                    if constexpr (HashBits == 32) {
493
                        uint32_t hash_value = HashUtil::murmur_hash3_32(raw_str, str_size,
494
                                                                        HashUtil::MURMUR3_32_SEED);
495
                        res_data[i].add(hash_value);
496
26
                    } else {
497
26
                        uint64_t hash_value = 0;
498
26
                        murmur_hash3_x64_64(raw_str, str_size, 0, &hash_value);
499
26
                        res_data[i].add(hash_value);
500
26
                    }
501
26
                }
502
27
            }
503
9
        }
504
9
    }
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
69
    static FunctionPtr create() { return std::make_shared<FunctionBitmapCount>(); }
514
515
60
    DataTypePtr get_return_type_impl(const DataTypes& arguments) const override {
516
60
        return std::make_shared<DataTypeInt64>();
517
60
    }
518
519
60
    size_t get_number_of_arguments() const override { return 1; }
520
521
157
    bool use_default_implementation_for_nulls() const override { return false; }
522
523
    Status execute_impl(FunctionContext* context, Block& block, const ColumnNumbers& arguments,
524
97
                        uint32_t result, size_t input_rows_count) const override {
525
97
        auto res_data_column = ColumnInt64::create();
526
97
        auto& res = res_data_column->get_data();
527
97
        auto data_null_map = ColumnUInt8::create(input_rows_count, 0);
528
97
        auto& null_map = data_null_map->get_data();
529
530
97
        auto column = block.get_by_position(arguments[0]).column;
531
97
        if (auto* nullable = check_and_get_column<const ColumnNullable>(*column)) {
532
9
            VectorizedUtils::update_null_map(null_map, nullable->get_null_map_data());
533
9
            column = nullable->get_nested_column_ptr();
534
9
        }
535
97
        auto str_col = assert_cast<const ColumnBitmap*>(column.get());
536
97
        const auto& col_data = str_col->get_data();
537
538
97
        res.reserve(input_rows_count);
539
281
        for (size_t i = 0; i < input_rows_count; ++i) {
540
184
            if (null_map[i]) {
541
7
                res.push_back(0);
542
7
                continue;
543
7
            }
544
177
            res.push_back(col_data[i].cardinality());
545
177
        }
546
97
        block.replace_by_position(result, std::move(res_data_column));
547
97
        return Status::OK();
548
97
    }
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
25
    static void vector_vector(const TData& lvec, const TData& rvec, TData& res) {
563
25
        size_t size = lvec.size();
564
101
        for (size_t i = 0; i < size; ++i) {
565
76
            res[i] = lvec[i];
566
76
            res[i] -= rvec[i];
567
76
        }
568
25
    }
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 NameBitmapAndNotCount {
586
    static constexpr auto name = "bitmap_and_not_count";
587
};
588
589
template <typename LeftDataType, typename RightDataType>
590
struct BitmapAndNotCount {
591
    using ResultDataType = DataTypeInt64;
592
    using T0 = typename LeftDataType::FieldType;
593
    using T1 = typename RightDataType::FieldType;
594
    using TData = std::vector<BitmapValue>;
595
    using ResTData = typename ColumnInt64::Container::value_type;
596
597
36
    static void vector_vector(const TData& lvec, const TData& rvec, ResTData* res) {
598
36
        size_t size = lvec.size();
599
128
        for (size_t i = 0; i < size; ++i) {
600
92
            res[i] = lvec[i].andnot_cardinality(rvec[i]);
601
92
        }
602
36
    }
603
0
    static void scalar_vector(const BitmapValue& lval, const TData& rvec, ResTData* res) {
604
0
        size_t size = rvec.size();
605
0
        for (size_t i = 0; i < size; ++i) {
606
0
            res[i] = lval.andnot_cardinality(rvec[i]);
607
0
        }
608
0
    }
609
0
    static void vector_scalar(const TData& lvec, const BitmapValue& rval, ResTData* res) {
610
0
        size_t size = lvec.size();
611
0
        for (size_t i = 0; i < size; ++i) {
612
0
            res[i] = lvec[i].andnot_cardinality(rval);
613
0
        }
614
0
    }
615
};
616
617
97
void update_bitmap_op_count(int64_t* __restrict count, const NullMap& null_map) {
618
97
    static constexpr int64_t flags[2] = {-1, 0};
619
97
    size_t size = null_map.size();
620
97
    auto* __restrict null_map_data = null_map.data();
621
284
    for (size_t i = 0; i < size; ++i) {
622
187
        count[i] &= flags[null_map_data[i]];
623
187
    }
624
97
}
625
626
// for bitmap_and_count, bitmap_xor_count and bitmap_and_not_count,
627
// result is 0 for rows that if any column is null value
628
ColumnPtr handle_bitmap_op_count_null_value(ColumnPtr& src, const Block& block,
629
                                            const ColumnNumbers& args, uint32_t result,
630
51
                                            size_t input_rows_count) {
631
51
    MutableColumnPtr mutable_src = IColumn::mutate(std::move(src));
632
51
    auto* src_not_nullable_mutable = mutable_src.get();
633
51
    if (auto* nullable = check_and_get_column<ColumnNullable>(*mutable_src)) {
634
6
        src_not_nullable_mutable = &nullable->get_nested_column();
635
6
    }
636
51
    auto* __restrict count_data =
637
51
            assert_cast<ColumnInt64*>(src_not_nullable_mutable)->get_data().data();
638
639
114
    for (const auto& arg : args) {
640
114
        const ColumnWithTypeAndName& elem = block.get_by_position(arg);
641
114
        if (!elem.type->is_nullable()) {
642
17
            continue;
643
17
        }
644
645
97
        bool is_const = is_column_const(*elem.column);
646
        /// Const Nullable that are NULL.
647
97
        if (is_const && assert_cast<const ColumnConst*>(elem.column.get())->only_null()) {
648
0
            return block.get_by_position(result).type->create_column_const(
649
0
                    input_rows_count, Field::create_field<TYPE_BIGINT>(0));
650
0
        }
651
97
        if (is_const) {
652
0
            continue;
653
0
        }
654
655
97
        if (const auto* nullable_column = assert_cast<const ColumnNullable*>(elem.column.get())) {
656
97
            const ColumnPtr& null_map_column = nullable_column->get_null_map_column_ptr();
657
97
            const NullMap& src_null_map =
658
97
                    assert_cast<const ColumnUInt8&>(*null_map_column).get_data();
659
660
97
            update_bitmap_op_count(count_data, src_null_map);
661
97
        }
662
97
    }
663
664
51
    return mutable_src;
665
51
}
666
667
Status execute_bitmap_op_count_null_to_zero(
668
        FunctionContext* context, Block& block, const ColumnNumbers& arguments, uint32_t result,
669
        size_t input_rows_count,
670
        const std::function<Status(FunctionContext*, Block&, const ColumnNumbers&, size_t, size_t)>&
671
100
                exec_impl_func) {
672
100
    if (have_null_column(block, arguments)) {
673
51
        auto [temporary_block, new_args, new_result] =
674
51
                create_block_with_nested_columns(block, arguments, result);
675
51
        RETURN_IF_ERROR(exec_impl_func(context, temporary_block, new_args, new_result,
676
51
                                       temporary_block.rows()));
677
51
        block.get_by_position(result).column = handle_bitmap_op_count_null_value(
678
51
                temporary_block.get_by_position(new_result).column, block, arguments, result,
679
51
                input_rows_count);
680
51
    } else {
681
49
        return exec_impl_func(context, block, arguments, result, input_rows_count);
682
49
    }
683
51
    return Status::OK();
684
100
}
685
686
template <typename FunctionName, bool NewVersion = false>
687
class FunctionBitmapAndNotCount : public IFunction {
688
public:
689
    using LeftDataType = DataTypeBitMap;
690
    using RightDataType = DataTypeBitMap;
691
    using ResultDataType = typename BitmapAndNotCount<LeftDataType, RightDataType>::ResultDataType;
692
693
    static constexpr auto name = NewVersion ? "bitmap_and_not_count_v2" : FunctionName::name;
694
42
    static FunctionPtr create() { return std::make_shared<FunctionBitmapAndNotCount>(); }
_ZN5doris25FunctionBitmapAndNotCountINS_21NameBitmapAndNotCountELb0EE6createEv
Line
Count
Source
694
12
    static FunctionPtr create() { return std::make_shared<FunctionBitmapAndNotCount>(); }
_ZN5doris25FunctionBitmapAndNotCountINS_21NameBitmapAndNotCountELb1EE6createEv
Line
Count
Source
694
30
    static FunctionPtr create() { return std::make_shared<FunctionBitmapAndNotCount>(); }
695
3
    String get_name() const override { return name; }
_ZNK5doris25FunctionBitmapAndNotCountINS_21NameBitmapAndNotCountELb0EE8get_nameB5cxx11Ev
Line
Count
Source
695
1
    String get_name() const override { return name; }
_ZNK5doris25FunctionBitmapAndNotCountINS_21NameBitmapAndNotCountELb1EE8get_nameB5cxx11Ev
Line
Count
Source
695
2
    String get_name() const override { return name; }
696
24
    size_t get_number_of_arguments() const override { return 2; }
_ZNK5doris25FunctionBitmapAndNotCountINS_21NameBitmapAndNotCountELb0EE23get_number_of_argumentsEv
Line
Count
Source
696
3
    size_t get_number_of_arguments() const override { return 2; }
_ZNK5doris25FunctionBitmapAndNotCountINS_21NameBitmapAndNotCountELb1EE23get_number_of_argumentsEv
Line
Count
Source
696
21
    size_t get_number_of_arguments() const override { return 2; }
697
24
    DataTypePtr get_return_type_impl(const DataTypes& arguments) const override {
698
24
        if constexpr (NewVersion) {
699
21
            return std::make_shared<ResultDataType>();
700
21
        } else {
701
3
            bool return_nullable = false;
702
            // result is nullable only when any columns is nullable for bitmap_and_not_count
703
3
            for (size_t i = 0; i < arguments.size(); ++i) {
704
3
                if (arguments[i]->is_nullable()) {
705
3
                    return_nullable = true;
706
3
                    break;
707
3
                }
708
3
            }
709
3
            auto result_type = std::make_shared<ResultDataType>();
710
3
            return return_nullable ? make_nullable(result_type) : result_type;
711
3
        }
712
24
    }
_ZNK5doris25FunctionBitmapAndNotCountINS_21NameBitmapAndNotCountELb0EE20get_return_type_implERKSt6vectorISt10shared_ptrIKNS_9IDataTypeEESaIS7_EE
Line
Count
Source
697
3
    DataTypePtr get_return_type_impl(const DataTypes& arguments) const override {
698
        if constexpr (NewVersion) {
699
            return std::make_shared<ResultDataType>();
700
3
        } else {
701
3
            bool return_nullable = false;
702
            // result is nullable only when any columns is nullable for bitmap_and_not_count
703
3
            for (size_t i = 0; i < arguments.size(); ++i) {
704
3
                if (arguments[i]->is_nullable()) {
705
3
                    return_nullable = true;
706
3
                    break;
707
3
                }
708
3
            }
709
3
            auto result_type = std::make_shared<ResultDataType>();
710
3
            return return_nullable ? make_nullable(result_type) : result_type;
711
3
        }
712
3
    }
_ZNK5doris25FunctionBitmapAndNotCountINS_21NameBitmapAndNotCountELb1EE20get_return_type_implERKSt6vectorISt10shared_ptrIKNS_9IDataTypeEESaIS7_EE
Line
Count
Source
697
21
    DataTypePtr get_return_type_impl(const DataTypes& arguments) const override {
698
21
        if constexpr (NewVersion) {
699
21
            return std::make_shared<ResultDataType>();
700
        } else {
701
            bool return_nullable = false;
702
            // result is nullable only when any columns is nullable for bitmap_and_not_count
703
            for (size_t i = 0; i < arguments.size(); ++i) {
704
                if (arguments[i]->is_nullable()) {
705
                    return_nullable = true;
706
                    break;
707
                }
708
            }
709
            auto result_type = std::make_shared<ResultDataType>();
710
            return return_nullable ? make_nullable(result_type) : result_type;
711
        }
712
21
    }
713
714
60
    bool use_default_implementation_for_nulls() const override {
715
        // for bitmap_and_not_count, result is always not null, and if the bitmap op result is null,
716
        // the count is 0
717
60
        return false;
718
60
    }
_ZNK5doris25FunctionBitmapAndNotCountINS_21NameBitmapAndNotCountELb0EE36use_default_implementation_for_nullsEv
Line
Count
Source
714
5
    bool use_default_implementation_for_nulls() const override {
715
        // for bitmap_and_not_count, result is always not null, and if the bitmap op result is null,
716
        // the count is 0
717
5
        return false;
718
5
    }
_ZNK5doris25FunctionBitmapAndNotCountINS_21NameBitmapAndNotCountELb1EE36use_default_implementation_for_nullsEv
Line
Count
Source
714
55
    bool use_default_implementation_for_nulls() const override {
715
        // for bitmap_and_not_count, result is always not null, and if the bitmap op result is null,
716
        // the count is 0
717
55
        return false;
718
55
    }
719
720
    Status execute_impl(FunctionContext* context, Block& block, const ColumnNumbers& arguments,
721
36
                        uint32_t result, size_t input_rows_count) const override {
722
36
        DCHECK_EQ(arguments.size(), 2);
723
36
        auto impl_func = [&](FunctionContext* context, Block& block, const ColumnNumbers& arguments,
724
36
                             uint32_t result, size_t input_rows_count) {
725
36
            return execute_impl_internal(context, block, arguments, result, input_rows_count);
726
36
        };
_ZZNK5doris25FunctionBitmapAndNotCountINS_21NameBitmapAndNotCountELb0EE12execute_implEPNS_15FunctionContextERNS_5BlockERKSt6vectorIjSaIjEEjmENKUlS4_S6_SB_jmE_clES4_S6_SB_jm
Line
Count
Source
724
2
                             uint32_t result, size_t input_rows_count) {
725
2
            return execute_impl_internal(context, block, arguments, result, input_rows_count);
726
2
        };
_ZZNK5doris25FunctionBitmapAndNotCountINS_21NameBitmapAndNotCountELb1EE12execute_implEPNS_15FunctionContextERNS_5BlockERKSt6vectorIjSaIjEEjmENKUlS4_S6_SB_jmE_clES4_S6_SB_jm
Line
Count
Source
724
34
                             uint32_t result, size_t input_rows_count) {
725
34
            return execute_impl_internal(context, block, arguments, result, input_rows_count);
726
34
        };
727
36
        return execute_bitmap_op_count_null_to_zero(context, block, arguments, result,
728
36
                                                    input_rows_count, impl_func);
729
36
    }
_ZNK5doris25FunctionBitmapAndNotCountINS_21NameBitmapAndNotCountELb0EE12execute_implEPNS_15FunctionContextERNS_5BlockERKSt6vectorIjSaIjEEjm
Line
Count
Source
721
2
                        uint32_t result, size_t input_rows_count) const override {
722
        DCHECK_EQ(arguments.size(), 2);
723
2
        auto impl_func = [&](FunctionContext* context, Block& block, const ColumnNumbers& arguments,
724
2
                             uint32_t result, size_t input_rows_count) {
725
2
            return execute_impl_internal(context, block, arguments, result, input_rows_count);
726
2
        };
727
2
        return execute_bitmap_op_count_null_to_zero(context, block, arguments, result,
728
2
                                                    input_rows_count, impl_func);
729
2
    }
_ZNK5doris25FunctionBitmapAndNotCountINS_21NameBitmapAndNotCountELb1EE12execute_implEPNS_15FunctionContextERNS_5BlockERKSt6vectorIjSaIjEEjm
Line
Count
Source
721
34
                        uint32_t result, size_t input_rows_count) const override {
722
        DCHECK_EQ(arguments.size(), 2);
723
34
        auto impl_func = [&](FunctionContext* context, Block& block, const ColumnNumbers& arguments,
724
34
                             uint32_t result, size_t input_rows_count) {
725
34
            return execute_impl_internal(context, block, arguments, result, input_rows_count);
726
34
        };
727
34
        return execute_bitmap_op_count_null_to_zero(context, block, arguments, result,
728
34
                                                    input_rows_count, impl_func);
729
34
    }
730
731
    Status execute_impl_internal(FunctionContext* context, Block& block,
732
                                 const ColumnNumbers& arguments, uint32_t result,
733
36
                                 size_t input_rows_count) const {
734
36
        using ColVecResult = ColumnVector<ResultDataType::PType>;
735
736
36
        typename ColVecResult::MutablePtr col_res = ColVecResult::create();
737
36
        auto& vec_res = col_res->get_data();
738
36
        vec_res.resize(block.rows());
739
740
36
        const auto& left = block.get_by_position(arguments[0]);
741
36
        auto lcol = left.column;
742
36
        const auto& right = block.get_by_position(arguments[1]);
743
36
        auto rcol = right.column;
744
745
36
        if (is_column_const(*left.column)) {
746
0
            BitmapAndNotCount<LeftDataType, RightDataType>::scalar_vector(
747
0
                    assert_cast<const ColumnBitmap&>(
748
0
                            assert_cast<const ColumnConst*>(lcol.get())->get_data_column())
749
0
                            .get_data()[0],
750
0
                    assert_cast<const ColumnBitmap*>(rcol.get())->get_data(), vec_res.data());
751
36
        } else if (is_column_const(*right.column)) {
752
0
            BitmapAndNotCount<LeftDataType, RightDataType>::vector_scalar(
753
0
                    assert_cast<const ColumnBitmap*>(lcol.get())->get_data(),
754
0
                    assert_cast<const ColumnBitmap&>(
755
0
                            assert_cast<const ColumnConst*>(rcol.get())->get_data_column())
756
0
                            .get_data()[0],
757
0
                    vec_res.data());
758
36
        } else {
759
36
            BitmapAndNotCount<LeftDataType, RightDataType>::vector_vector(
760
36
                    assert_cast<const ColumnBitmap*>(lcol.get())->get_data(),
761
36
                    assert_cast<const ColumnBitmap*>(rcol.get())->get_data(), vec_res.data());
762
36
        }
763
764
36
        auto& result_info = block.get_by_position(result);
765
36
        if (result_info.type->is_nullable()) {
766
2
            block.replace_by_position(
767
2
                    result, ColumnNullable::create(std::move(col_res),
768
2
                                                   ColumnUInt8::create(input_rows_count, 0)));
769
34
        } else {
770
34
            block.replace_by_position(result, std::move(col_res));
771
34
        }
772
36
        return Status::OK();
773
36
    }
_ZNK5doris25FunctionBitmapAndNotCountINS_21NameBitmapAndNotCountELb0EE21execute_impl_internalEPNS_15FunctionContextERNS_5BlockERKSt6vectorIjSaIjEEjm
Line
Count
Source
733
2
                                 size_t input_rows_count) const {
734
2
        using ColVecResult = ColumnVector<ResultDataType::PType>;
735
736
2
        typename ColVecResult::MutablePtr col_res = ColVecResult::create();
737
2
        auto& vec_res = col_res->get_data();
738
2
        vec_res.resize(block.rows());
739
740
2
        const auto& left = block.get_by_position(arguments[0]);
741
2
        auto lcol = left.column;
742
2
        const auto& right = block.get_by_position(arguments[1]);
743
2
        auto rcol = right.column;
744
745
2
        if (is_column_const(*left.column)) {
746
0
            BitmapAndNotCount<LeftDataType, RightDataType>::scalar_vector(
747
0
                    assert_cast<const ColumnBitmap&>(
748
0
                            assert_cast<const ColumnConst*>(lcol.get())->get_data_column())
749
0
                            .get_data()[0],
750
0
                    assert_cast<const ColumnBitmap*>(rcol.get())->get_data(), vec_res.data());
751
2
        } else if (is_column_const(*right.column)) {
752
0
            BitmapAndNotCount<LeftDataType, RightDataType>::vector_scalar(
753
0
                    assert_cast<const ColumnBitmap*>(lcol.get())->get_data(),
754
0
                    assert_cast<const ColumnBitmap&>(
755
0
                            assert_cast<const ColumnConst*>(rcol.get())->get_data_column())
756
0
                            .get_data()[0],
757
0
                    vec_res.data());
758
2
        } else {
759
2
            BitmapAndNotCount<LeftDataType, RightDataType>::vector_vector(
760
2
                    assert_cast<const ColumnBitmap*>(lcol.get())->get_data(),
761
2
                    assert_cast<const ColumnBitmap*>(rcol.get())->get_data(), vec_res.data());
762
2
        }
763
764
2
        auto& result_info = block.get_by_position(result);
765
2
        if (result_info.type->is_nullable()) {
766
2
            block.replace_by_position(
767
2
                    result, ColumnNullable::create(std::move(col_res),
768
2
                                                   ColumnUInt8::create(input_rows_count, 0)));
769
2
        } else {
770
0
            block.replace_by_position(result, std::move(col_res));
771
0
        }
772
2
        return Status::OK();
773
2
    }
_ZNK5doris25FunctionBitmapAndNotCountINS_21NameBitmapAndNotCountELb1EE21execute_impl_internalEPNS_15FunctionContextERNS_5BlockERKSt6vectorIjSaIjEEjm
Line
Count
Source
733
34
                                 size_t input_rows_count) const {
734
34
        using ColVecResult = ColumnVector<ResultDataType::PType>;
735
736
34
        typename ColVecResult::MutablePtr col_res = ColVecResult::create();
737
34
        auto& vec_res = col_res->get_data();
738
34
        vec_res.resize(block.rows());
739
740
34
        const auto& left = block.get_by_position(arguments[0]);
741
34
        auto lcol = left.column;
742
34
        const auto& right = block.get_by_position(arguments[1]);
743
34
        auto rcol = right.column;
744
745
34
        if (is_column_const(*left.column)) {
746
0
            BitmapAndNotCount<LeftDataType, RightDataType>::scalar_vector(
747
0
                    assert_cast<const ColumnBitmap&>(
748
0
                            assert_cast<const ColumnConst*>(lcol.get())->get_data_column())
749
0
                            .get_data()[0],
750
0
                    assert_cast<const ColumnBitmap*>(rcol.get())->get_data(), vec_res.data());
751
34
        } else if (is_column_const(*right.column)) {
752
0
            BitmapAndNotCount<LeftDataType, RightDataType>::vector_scalar(
753
0
                    assert_cast<const ColumnBitmap*>(lcol.get())->get_data(),
754
0
                    assert_cast<const ColumnBitmap&>(
755
0
                            assert_cast<const ColumnConst*>(rcol.get())->get_data_column())
756
0
                            .get_data()[0],
757
0
                    vec_res.data());
758
34
        } else {
759
34
            BitmapAndNotCount<LeftDataType, RightDataType>::vector_vector(
760
34
                    assert_cast<const ColumnBitmap*>(lcol.get())->get_data(),
761
34
                    assert_cast<const ColumnBitmap*>(rcol.get())->get_data(), vec_res.data());
762
34
        }
763
764
34
        auto& result_info = block.get_by_position(result);
765
34
        if (result_info.type->is_nullable()) {
766
0
            block.replace_by_position(
767
0
                    result, ColumnNullable::create(std::move(col_res),
768
0
                                                   ColumnUInt8::create(input_rows_count, 0)));
769
34
        } else {
770
34
            block.replace_by_position(result, std::move(col_res));
771
34
        }
772
34
        return Status::OK();
773
34
    }
774
};
775
776
struct NameBitmapContains {
777
    static constexpr auto name = "bitmap_contains";
778
};
779
780
template <typename LeftDataType, typename RightDataType>
781
struct BitmapContains {
782
    using ResultDataType = DataTypeUInt8;
783
    using T0 = typename LeftDataType::FieldType;
784
    using T1 = typename RightDataType::FieldType;
785
    using LTData = std::vector<BitmapValue>;
786
    using RTData = typename ColumnVector<RightDataType::PType>::Container;
787
    using ResTData = typename ColumnUInt8::Container;
788
789
10
    static void vector_vector(const LTData& lvec, const RTData& rvec, ResTData& res) {
790
10
        size_t size = lvec.size();
791
37
        for (size_t i = 0; i < size; ++i) {
792
27
            res[i] = lvec[i].contains(rvec[i]);
793
27
        }
794
10
    }
795
410
    static void vector_scalar(const LTData& lvec, const T1& rval, ResTData& res) {
796
410
        size_t size = lvec.size();
797
820
        for (size_t i = 0; i < size; ++i) {
798
410
            res[i] = lvec[i].contains(rval);
799
410
        }
800
410
    }
801
0
    static void scalar_vector(const BitmapValue& lval, const RTData& rvec, ResTData& res) {
802
0
        size_t size = rvec.size();
803
0
        for (size_t i = 0; i < size; ++i) {
804
0
            res[i] = lval.contains(rvec[i]);
805
0
        }
806
0
    }
807
};
808
809
struct NameBitmapRemove {
810
    static constexpr auto name = "bitmap_remove";
811
};
812
813
template <typename LeftDataType, typename RightDataType>
814
struct BitmapRemove {
815
    using ResultDataType = DataTypeBitMap;
816
    using T0 = typename LeftDataType::FieldType;
817
    using T1 = typename RightDataType::FieldType;
818
    using LTData = std::vector<BitmapValue>;
819
    using RTData = typename ColumnVector<RightDataType::PType>::Container;
820
    using ResTData = std::vector<BitmapValue>;
821
822
2
    static void vector_vector(const LTData& lvec, const RTData& rvec, ResTData& res) {
823
2
        size_t size = lvec.size();
824
6
        for (size_t i = 0; i < size; ++i) {
825
4
            res[i] = lvec[i];
826
4
            res[i].remove(rvec[i]);
827
4
        }
828
2
    }
829
12
    static void vector_scalar(const LTData& lvec, const T1& rval, ResTData& res) {
830
12
        size_t size = lvec.size();
831
45
        for (size_t i = 0; i < size; ++i) {
832
33
            res[i] = lvec[i];
833
33
            res[i].remove(rval);
834
33
        }
835
12
    }
836
0
    static void scalar_vector(const BitmapValue& lval, const RTData& rvec, ResTData& res) {
837
0
        size_t size = rvec.size();
838
0
        for (size_t i = 0; i < size; ++i) {
839
0
            res[i] = lval;
840
0
            res[i].remove(rvec[i]);
841
0
        }
842
0
    }
843
};
844
845
struct NameBitmapHasAny {
846
    static constexpr auto name = "bitmap_has_any";
847
};
848
849
template <typename LeftDataType, typename RightDataType>
850
struct BitmapHasAny {
851
    using ResultDataType = DataTypeUInt8;
852
    using T0 = typename LeftDataType::FieldType;
853
    using T1 = typename RightDataType::FieldType;
854
    using TData = std::vector<BitmapValue>;
855
    using ResTData = typename ColumnUInt8::Container;
856
857
15
    static void vector_vector(const TData& lvec, const TData& rvec, ResTData& res) {
858
15
        size_t size = lvec.size();
859
47
        for (size_t i = 0; i < size; ++i) {
860
32
            res[i] = lvec[i].intersects(rvec[i]);
861
32
        }
862
15
    }
863
0
    static void vector_scalar(const TData& lvec, const BitmapValue& rval, ResTData& res) {
864
0
        size_t size = lvec.size();
865
0
        for (size_t i = 0; i < size; ++i) {
866
0
            res[i] = lvec[i].intersects(rval);
867
0
        }
868
0
    }
869
0
    static void scalar_vector(const BitmapValue& lval, const TData& rvec, ResTData& res) {
870
0
        size_t size = rvec.size();
871
0
        for (size_t i = 0; i < size; ++i) {
872
0
            res[i] = lval.intersects(rvec[i]);
873
0
        }
874
0
    }
875
};
876
877
struct NameBitmapHasAll {
878
    static constexpr auto name = "bitmap_has_all";
879
};
880
881
template <typename LeftDataType, typename RightDataType>
882
struct BitmapHasAll {
883
    using ResultDataType = DataTypeUInt8;
884
    using T0 = typename LeftDataType::FieldType;
885
    using T1 = typename RightDataType::FieldType;
886
    using TData = std::vector<BitmapValue>;
887
    using ResTData = typename ColumnUInt8::Container;
888
889
13
    static void vector_vector(const TData& lvec, const TData& rvec, ResTData& res) {
890
13
        size_t size = lvec.size();
891
47
        for (size_t i = 0; i < size; ++i) {
892
34
            res[i] = lvec[i].contains_all(rvec[i]);
893
34
        }
894
13
    }
895
0
    static void vector_scalar(const TData& lvec, const BitmapValue& rval, ResTData& res) {
896
0
        size_t size = lvec.size();
897
0
        for (size_t i = 0; i < size; ++i) {
898
0
            res[i] = lvec[i].contains_all(rval);
899
0
        }
900
0
    }
901
0
    static void scalar_vector(const BitmapValue& lval, const TData& rvec, ResTData& res) {
902
0
        size_t size = rvec.size();
903
0
        for (size_t i = 0; i < size; ++i) {
904
0
            res[i] = lval.contains_all(rvec[i]);
905
0
        }
906
0
    }
907
};
908
909
struct NameBitmapToString {
910
    static constexpr auto name = "bitmap_to_string";
911
};
912
913
struct BitmapToString {
914
    using ReturnType = DataTypeString;
915
    static constexpr auto PrimitiveTypeImpl = PrimitiveType::TYPE_BITMAP;
916
    using Type = DataTypeBitMap::FieldType;
917
    using ReturnColumnType = ColumnString;
918
    using Chars = ColumnString::Chars;
919
    using Offsets = ColumnString::Offsets;
920
921
233
    static Status vector(const std::vector<BitmapValue>& data, Chars& chars, Offsets& offsets) {
922
233
        size_t size = data.size();
923
233
        offsets.resize(size);
924
233
        chars.reserve(size);
925
1.20k
        for (size_t i = 0; i < size; ++i) {
926
967
            StringOP::push_value_string(data[i].to_string(), i, chars, offsets);
927
967
        }
928
233
        return Status::OK();
929
233
    }
930
};
931
932
struct NameBitmapToBase64 {
933
    static constexpr auto name = "bitmap_to_base64";
934
};
935
936
struct BitmapToBase64 {
937
    using ReturnType = DataTypeString;
938
    static constexpr auto PrimitiveTypeImpl = PrimitiveType::TYPE_BITMAP;
939
    using Type = DataTypeBitMap::FieldType;
940
    using ReturnColumnType = ColumnString;
941
    using Chars = ColumnString::Chars;
942
    using Offsets = ColumnString::Offsets;
943
944
    // ColumnString not support 64bit, only 32bit, so that the max size is 4G
945
25
    static Status vector(const std::vector<BitmapValue>& data, Chars& chars, Offsets& offsets) {
946
25
        size_t size = data.size();
947
25
        offsets.resize(size);
948
25
        size_t output_char_size = 0;
949
71
        for (size_t i = 0; i < size; ++i) {
950
46
            const BitmapValue& bitmap_val = data[i];
951
46
            auto ser_size = bitmap_val.getSizeInBytes();
952
46
            output_char_size += (int)(4.0 * ceil((double)ser_size / 3.0));
953
46
        }
954
25
        ColumnString::check_chars_length(output_char_size, size);
955
25
        chars.resize(output_char_size);
956
25
        auto chars_data = chars.data();
957
958
25
        size_t cur_ser_size = 0;
959
25
        size_t last_ser_size = 0;
960
25
        std::string ser_buff;
961
25
        size_t encoded_offset = 0;
962
71
        for (size_t i = 0; i < size; ++i) {
963
46
            const BitmapValue& bitmap_val = data[i];
964
46
            cur_ser_size = bitmap_val.getSizeInBytes();
965
46
            if (cur_ser_size > last_ser_size) {
966
33
                last_ser_size = cur_ser_size;
967
33
                ser_buff.resize(cur_ser_size);
968
33
            }
969
46
            bitmap_val.write_to(ser_buff.data());
970
971
46
            auto outlen = base64_encode((const unsigned char*)ser_buff.data(), cur_ser_size,
972
46
                                        chars_data + encoded_offset);
973
46
            DCHECK(outlen > 0);
974
975
46
            encoded_offset += (int)(4.0 * ceil((double)cur_ser_size / 3.0));
976
46
            offsets[i] = cast_set<UInt32>(encoded_offset);
977
46
        }
978
25
        return Status::OK();
979
25
    }
980
};
981
982
struct SubBitmap {
983
    static constexpr auto name = "sub_bitmap";
984
    using TData1 = std::vector<BitmapValue>;
985
    using TData2 = typename ColumnInt64::Container;
986
987
    static void vector3(const TData1& bitmap_data, const TData2& offset_data,
988
                        const TData2& limit_data, NullMap& null_map, size_t input_rows_count,
989
13
                        TData1& res) {
990
43
        for (int i = 0; i < input_rows_count; ++i) {
991
30
            if (null_map[i]) {
992
0
                continue;
993
0
            }
994
30
            if (limit_data[i] <= 0) {
995
1
                null_map[i] = 1;
996
1
                continue;
997
1
            }
998
29
            if (bitmap_data[i].offset_limit(offset_data[i], limit_data[i], &res[i]) == 0) {
999
24
                null_map[i] = 1;
1000
24
            }
1001
29
        }
1002
13
    }
1003
    static void vector_scalars(const TData1& bitmap_data, const Int64& offset_data,
1004
                               const Int64& limit_data, NullMap& null_map, size_t input_rows_count,
1005
0
                               TData1& res) {
1006
0
        for (int i = 0; i < input_rows_count; ++i) {
1007
0
            if (null_map[i]) {
1008
0
                continue;
1009
0
            }
1010
0
            if (limit_data <= 0) {
1011
0
                null_map[i] = 1;
1012
0
                continue;
1013
0
            }
1014
0
            if (bitmap_data[i].offset_limit(offset_data, limit_data, &res[i]) == 0) {
1015
0
                null_map[i] = 1;
1016
0
            }
1017
0
        }
1018
0
    }
1019
};
1020
1021
struct BitmapSubsetLimit {
1022
    static constexpr auto name = "bitmap_subset_limit";
1023
    using TData1 = std::vector<BitmapValue>;
1024
    using TData2 = typename ColumnInt64::Container;
1025
1026
    static void vector3(const TData1& bitmap_data, const TData2& offset_data,
1027
                        const TData2& limit_data, NullMap& null_map, size_t input_rows_count,
1028
11
                        TData1& res) {
1029
39
        for (int i = 0; i < input_rows_count; ++i) {
1030
28
            if (null_map[i]) {
1031
0
                continue;
1032
0
            }
1033
28
            if (offset_data[i] < 0 || limit_data[i] < 0) {
1034
0
                null_map[i] = 1;
1035
0
                continue;
1036
0
            }
1037
28
            bitmap_data[i].sub_limit(offset_data[i], limit_data[i], &res[i]);
1038
28
        }
1039
11
    }
1040
    static void vector_scalars(const TData1& bitmap_data, const Int64& offset_data,
1041
                               const Int64& limit_data, NullMap& null_map, size_t input_rows_count,
1042
0
                               TData1& res) {
1043
0
        for (int i = 0; i < input_rows_count; ++i) {
1044
0
            if (null_map[i]) {
1045
0
                continue;
1046
0
            }
1047
0
            if (offset_data < 0 || limit_data < 0) {
1048
0
                null_map[i] = 1;
1049
0
                continue;
1050
0
            }
1051
0
            bitmap_data[i].sub_limit(offset_data, limit_data, &res[i]);
1052
0
        }
1053
0
    }
1054
};
1055
1056
struct BitmapSubsetInRange {
1057
    static constexpr auto name = "bitmap_subset_in_range";
1058
    using TData1 = std::vector<BitmapValue>;
1059
    using TData2 = typename ColumnInt64::Container;
1060
1061
    static void vector3(const TData1& bitmap_data, const TData2& range_start,
1062
                        const TData2& range_end, NullMap& null_map, size_t input_rows_count,
1063
11
                        TData1& res) {
1064
39
        for (int i = 0; i < input_rows_count; ++i) {
1065
28
            if (null_map[i]) {
1066
0
                continue;
1067
0
            }
1068
28
            if (range_start[i] >= range_end[i] || range_start[i] < 0 || range_end[i] < 0) {
1069
25
                null_map[i] = 1;
1070
25
                continue;
1071
25
            }
1072
3
            bitmap_data[i].sub_range(range_start[i], range_end[i], &res[i]);
1073
3
        }
1074
11
    }
1075
    static void vector_scalars(const TData1& bitmap_data, const Int64& range_start,
1076
                               const Int64& range_end, NullMap& null_map, size_t input_rows_count,
1077
0
                               TData1& res) {
1078
0
        for (int i = 0; i < input_rows_count; ++i) {
1079
0
            if (null_map[i]) {
1080
0
                continue;
1081
0
            }
1082
0
            if (range_start >= range_end || range_start < 0 || range_end < 0) {
1083
0
                null_map[i] = 1;
1084
0
                continue;
1085
0
            }
1086
0
            bitmap_data[i].sub_range(range_start, range_end, &res[i]);
1087
0
        }
1088
0
    }
1089
};
1090
1091
template <typename Impl>
1092
class FunctionBitmapSubs : public IFunction {
1093
public:
1094
    static constexpr auto name = Impl::name;
1095
3
    String get_name() const override { return name; }
_ZNK5doris18FunctionBitmapSubsINS_9SubBitmapEE8get_nameB5cxx11Ev
Line
Count
Source
1095
1
    String get_name() const override { return name; }
_ZNK5doris18FunctionBitmapSubsINS_17BitmapSubsetLimitEE8get_nameB5cxx11Ev
Line
Count
Source
1095
1
    String get_name() const override { return name; }
_ZNK5doris18FunctionBitmapSubsINS_19BitmapSubsetInRangeEE8get_nameB5cxx11Ev
Line
Count
Source
1095
1
    String get_name() const override { return name; }
1096
1097
44
    static FunctionPtr create() { return std::make_shared<FunctionBitmapSubs>(); }
_ZN5doris18FunctionBitmapSubsINS_9SubBitmapEE6createEv
Line
Count
Source
1097
16
    static FunctionPtr create() { return std::make_shared<FunctionBitmapSubs>(); }
_ZN5doris18FunctionBitmapSubsINS_17BitmapSubsetLimitEE6createEv
Line
Count
Source
1097
14
    static FunctionPtr create() { return std::make_shared<FunctionBitmapSubs>(); }
_ZN5doris18FunctionBitmapSubsINS_19BitmapSubsetInRangeEE6createEv
Line
Count
Source
1097
14
    static FunctionPtr create() { return std::make_shared<FunctionBitmapSubs>(); }
1098
1099
17
    DataTypePtr get_return_type_impl(const DataTypes& arguments) const override {
1100
17
        return make_nullable(std::make_shared<DataTypeBitMap>());
1101
17
    }
_ZNK5doris18FunctionBitmapSubsINS_9SubBitmapEE20get_return_type_implERKSt6vectorISt10shared_ptrIKNS_9IDataTypeEESaIS7_EE
Line
Count
Source
1099
7
    DataTypePtr get_return_type_impl(const DataTypes& arguments) const override {
1100
7
        return make_nullable(std::make_shared<DataTypeBitMap>());
1101
7
    }
_ZNK5doris18FunctionBitmapSubsINS_17BitmapSubsetLimitEE20get_return_type_implERKSt6vectorISt10shared_ptrIKNS_9IDataTypeEESaIS7_EE
Line
Count
Source
1099
5
    DataTypePtr get_return_type_impl(const DataTypes& arguments) const override {
1100
5
        return make_nullable(std::make_shared<DataTypeBitMap>());
1101
5
    }
_ZNK5doris18FunctionBitmapSubsINS_19BitmapSubsetInRangeEE20get_return_type_implERKSt6vectorISt10shared_ptrIKNS_9IDataTypeEESaIS7_EE
Line
Count
Source
1099
5
    DataTypePtr get_return_type_impl(const DataTypes& arguments) const override {
1100
5
        return make_nullable(std::make_shared<DataTypeBitMap>());
1101
5
    }
1102
1103
17
    size_t get_number_of_arguments() const override { return 3; }
_ZNK5doris18FunctionBitmapSubsINS_9SubBitmapEE23get_number_of_argumentsEv
Line
Count
Source
1103
7
    size_t get_number_of_arguments() const override { return 3; }
_ZNK5doris18FunctionBitmapSubsINS_17BitmapSubsetLimitEE23get_number_of_argumentsEv
Line
Count
Source
1103
5
    size_t get_number_of_arguments() const override { return 3; }
_ZNK5doris18FunctionBitmapSubsINS_19BitmapSubsetInRangeEE23get_number_of_argumentsEv
Line
Count
Source
1103
5
    size_t get_number_of_arguments() const override { return 3; }
1104
1105
    Status execute_impl(FunctionContext* context, Block& block, const ColumnNumbers& arguments,
1106
35
                        uint32_t result, size_t input_rows_count) const override {
1107
35
        DCHECK_EQ(arguments.size(), 3);
1108
35
        auto res_null_map = ColumnUInt8::create(input_rows_count, 0);
1109
35
        auto res_data_column = ColumnBitmap::create(input_rows_count);
1110
1111
35
        bool col_const[3];
1112
35
        ColumnPtr argument_columns[3];
1113
140
        for (int i = 0; i < 3; ++i) {
1114
105
            col_const[i] = is_column_const(*block.get_by_position(arguments[i]).column);
1115
105
        }
1116
35
        argument_columns[0] = col_const[0] ? static_cast<const ColumnConst&>(
1117
0
                                                     *block.get_by_position(arguments[0]).column)
1118
0
                                                     .convert_to_full_column()
1119
35
                                           : block.get_by_position(arguments[0]).column;
1120
1121
35
        default_preprocess_parameter_columns(argument_columns, col_const, {1, 2}, block, arguments);
1122
1123
35
        auto bitmap_column = assert_cast<const ColumnBitmap*>(argument_columns[0].get());
1124
35
        auto offset_column = assert_cast<const ColumnInt64*>(argument_columns[1].get());
1125
35
        auto limit_column = assert_cast<const ColumnInt64*>(argument_columns[2].get());
1126
1127
35
        if (col_const[1] && col_const[2]) {
1128
0
            Impl::vector_scalars(bitmap_column->get_data(), offset_column->get_element(0),
1129
0
                                 limit_column->get_element(0), res_null_map->get_data(),
1130
0
                                 input_rows_count, res_data_column->get_data());
1131
35
        } else {
1132
35
            Impl::vector3(bitmap_column->get_data(), offset_column->get_data(),
1133
35
                          limit_column->get_data(), res_null_map->get_data(), input_rows_count,
1134
35
                          res_data_column->get_data());
1135
35
        }
1136
1137
35
        block.get_by_position(result).column =
1138
35
                ColumnNullable::create(std::move(res_data_column), std::move(res_null_map));
1139
35
        return Status::OK();
1140
35
    }
_ZNK5doris18FunctionBitmapSubsINS_9SubBitmapEE12execute_implEPNS_15FunctionContextERNS_5BlockERKSt6vectorIjSaIjEEjm
Line
Count
Source
1106
13
                        uint32_t result, size_t input_rows_count) const override {
1107
13
        DCHECK_EQ(arguments.size(), 3);
1108
13
        auto res_null_map = ColumnUInt8::create(input_rows_count, 0);
1109
13
        auto res_data_column = ColumnBitmap::create(input_rows_count);
1110
1111
13
        bool col_const[3];
1112
13
        ColumnPtr argument_columns[3];
1113
52
        for (int i = 0; i < 3; ++i) {
1114
39
            col_const[i] = is_column_const(*block.get_by_position(arguments[i]).column);
1115
39
        }
1116
13
        argument_columns[0] = col_const[0] ? static_cast<const ColumnConst&>(
1117
0
                                                     *block.get_by_position(arguments[0]).column)
1118
0
                                                     .convert_to_full_column()
1119
13
                                           : block.get_by_position(arguments[0]).column;
1120
1121
13
        default_preprocess_parameter_columns(argument_columns, col_const, {1, 2}, block, arguments);
1122
1123
13
        auto bitmap_column = assert_cast<const ColumnBitmap*>(argument_columns[0].get());
1124
13
        auto offset_column = assert_cast<const ColumnInt64*>(argument_columns[1].get());
1125
13
        auto limit_column = assert_cast<const ColumnInt64*>(argument_columns[2].get());
1126
1127
13
        if (col_const[1] && col_const[2]) {
1128
0
            Impl::vector_scalars(bitmap_column->get_data(), offset_column->get_element(0),
1129
0
                                 limit_column->get_element(0), res_null_map->get_data(),
1130
0
                                 input_rows_count, res_data_column->get_data());
1131
13
        } else {
1132
13
            Impl::vector3(bitmap_column->get_data(), offset_column->get_data(),
1133
13
                          limit_column->get_data(), res_null_map->get_data(), input_rows_count,
1134
13
                          res_data_column->get_data());
1135
13
        }
1136
1137
13
        block.get_by_position(result).column =
1138
13
                ColumnNullable::create(std::move(res_data_column), std::move(res_null_map));
1139
13
        return Status::OK();
1140
13
    }
_ZNK5doris18FunctionBitmapSubsINS_17BitmapSubsetLimitEE12execute_implEPNS_15FunctionContextERNS_5BlockERKSt6vectorIjSaIjEEjm
Line
Count
Source
1106
11
                        uint32_t result, size_t input_rows_count) const override {
1107
11
        DCHECK_EQ(arguments.size(), 3);
1108
11
        auto res_null_map = ColumnUInt8::create(input_rows_count, 0);
1109
11
        auto res_data_column = ColumnBitmap::create(input_rows_count);
1110
1111
11
        bool col_const[3];
1112
11
        ColumnPtr argument_columns[3];
1113
44
        for (int i = 0; i < 3; ++i) {
1114
33
            col_const[i] = is_column_const(*block.get_by_position(arguments[i]).column);
1115
33
        }
1116
11
        argument_columns[0] = col_const[0] ? static_cast<const ColumnConst&>(
1117
0
                                                     *block.get_by_position(arguments[0]).column)
1118
0
                                                     .convert_to_full_column()
1119
11
                                           : block.get_by_position(arguments[0]).column;
1120
1121
11
        default_preprocess_parameter_columns(argument_columns, col_const, {1, 2}, block, arguments);
1122
1123
11
        auto bitmap_column = assert_cast<const ColumnBitmap*>(argument_columns[0].get());
1124
11
        auto offset_column = assert_cast<const ColumnInt64*>(argument_columns[1].get());
1125
11
        auto limit_column = assert_cast<const ColumnInt64*>(argument_columns[2].get());
1126
1127
11
        if (col_const[1] && col_const[2]) {
1128
0
            Impl::vector_scalars(bitmap_column->get_data(), offset_column->get_element(0),
1129
0
                                 limit_column->get_element(0), res_null_map->get_data(),
1130
0
                                 input_rows_count, res_data_column->get_data());
1131
11
        } else {
1132
11
            Impl::vector3(bitmap_column->get_data(), offset_column->get_data(),
1133
11
                          limit_column->get_data(), res_null_map->get_data(), input_rows_count,
1134
11
                          res_data_column->get_data());
1135
11
        }
1136
1137
11
        block.get_by_position(result).column =
1138
11
                ColumnNullable::create(std::move(res_data_column), std::move(res_null_map));
1139
11
        return Status::OK();
1140
11
    }
_ZNK5doris18FunctionBitmapSubsINS_19BitmapSubsetInRangeEE12execute_implEPNS_15FunctionContextERNS_5BlockERKSt6vectorIjSaIjEEjm
Line
Count
Source
1106
11
                        uint32_t result, size_t input_rows_count) const override {
1107
11
        DCHECK_EQ(arguments.size(), 3);
1108
11
        auto res_null_map = ColumnUInt8::create(input_rows_count, 0);
1109
11
        auto res_data_column = ColumnBitmap::create(input_rows_count);
1110
1111
11
        bool col_const[3];
1112
11
        ColumnPtr argument_columns[3];
1113
44
        for (int i = 0; i < 3; ++i) {
1114
33
            col_const[i] = is_column_const(*block.get_by_position(arguments[i]).column);
1115
33
        }
1116
11
        argument_columns[0] = col_const[0] ? static_cast<const ColumnConst&>(
1117
0
                                                     *block.get_by_position(arguments[0]).column)
1118
0
                                                     .convert_to_full_column()
1119
11
                                           : block.get_by_position(arguments[0]).column;
1120
1121
11
        default_preprocess_parameter_columns(argument_columns, col_const, {1, 2}, block, arguments);
1122
1123
11
        auto bitmap_column = assert_cast<const ColumnBitmap*>(argument_columns[0].get());
1124
11
        auto offset_column = assert_cast<const ColumnInt64*>(argument_columns[1].get());
1125
11
        auto limit_column = assert_cast<const ColumnInt64*>(argument_columns[2].get());
1126
1127
11
        if (col_const[1] && col_const[2]) {
1128
0
            Impl::vector_scalars(bitmap_column->get_data(), offset_column->get_element(0),
1129
0
                                 limit_column->get_element(0), res_null_map->get_data(),
1130
0
                                 input_rows_count, res_data_column->get_data());
1131
11
        } else {
1132
11
            Impl::vector3(bitmap_column->get_data(), offset_column->get_data(),
1133
11
                          limit_column->get_data(), res_null_map->get_data(), input_rows_count,
1134
11
                          res_data_column->get_data());
1135
11
        }
1136
1137
11
        block.get_by_position(result).column =
1138
11
                ColumnNullable::create(std::move(res_data_column), std::move(res_null_map));
1139
11
        return Status::OK();
1140
11
    }
1141
};
1142
1143
class FunctionBitmapToArray : public IFunction {
1144
public:
1145
    static constexpr auto name = "bitmap_to_array";
1146
1147
1
    String get_name() const override { return name; }
1148
1149
14
    static FunctionPtr create() { return std::make_shared<FunctionBitmapToArray>(); }
1150
1151
5
    DataTypePtr get_return_type_impl(const DataTypes& arguments) const override {
1152
5
        auto nested_type = make_nullable(std::make_shared<DataTypeInt64>());
1153
5
        return std::make_shared<DataTypeArray>(nested_type);
1154
5
    }
1155
1156
5
    size_t get_number_of_arguments() const override { return 1; }
1157
1158
    Status execute_impl(FunctionContext* context, Block& block, const ColumnNumbers& arguments,
1159
8
                        uint32_t result, size_t input_rows_count) const override {
1160
8
        auto return_nested_type = make_nullable(std::make_shared<DataTypeInt64>());
1161
8
        auto dest_array_column_ptr = ColumnArray::create(return_nested_type->create_column(),
1162
8
                                                         ColumnArray::ColumnOffsets::create());
1163
1164
8
        IColumn* dest_nested_column = &dest_array_column_ptr->get_data();
1165
8
        ColumnNullable* dest_nested_nullable_col =
1166
8
                reinterpret_cast<ColumnNullable*>(dest_nested_column);
1167
8
        dest_nested_column = dest_nested_nullable_col->get_nested_column_ptr().get();
1168
8
        auto& dest_nested_null_map = dest_nested_nullable_col->get_null_map_column().get_data();
1169
1170
8
        auto& arg_col = block.get_by_position(arguments[0]).column;
1171
8
        auto bitmap_col = assert_cast<const ColumnBitmap*>(arg_col.get());
1172
8
        const auto& bitmap_col_data = bitmap_col->get_data();
1173
8
        auto& nested_column_data = assert_cast<ColumnInt64*>(dest_nested_column)->get_data();
1174
8
        auto& dest_offsets = dest_array_column_ptr->get_offsets();
1175
8
        dest_offsets.reserve(input_rows_count);
1176
1177
16
        for (int i = 0; i < input_rows_count; ++i) {
1178
8
            bitmap_col_data[i].to_array(nested_column_data);
1179
8
            dest_nested_null_map.resize_fill(nested_column_data.size(), 0);
1180
8
            dest_offsets.push_back(nested_column_data.size());
1181
8
        }
1182
1183
8
        block.replace_by_position(result, std::move(dest_array_column_ptr));
1184
8
        return Status::OK();
1185
8
    }
1186
};
1187
1188
using FunctionBitmapEmpty = FunctionConst<BitmapEmpty, false>;
1189
using FunctionToBitmap = FunctionAlwaysNotNullable<ToBitmap>;
1190
using FunctionToBitmapWithCheck = FunctionAlwaysNotNullable<ToBitmapWithCheck, true>;
1191
1192
using FunctionBitmapFromString = FunctionBitmapAlwaysNull<BitmapFromString>;
1193
using FunctionBitmapFromArray = FunctionBitmapAlwaysNull<BitmapFromArray>;
1194
using FunctionBitmapHash = FunctionAlwaysNotNullable<BitmapHash<32>>;
1195
using FunctionBitmapHash64 = FunctionAlwaysNotNullable<BitmapHash<64>>;
1196
1197
using FunctionBitmapMin = FunctionBitmapSingle<FunctionBitmapMinImpl>;
1198
using FunctionBitmapMax = FunctionBitmapSingle<FunctionBitmapMaxImpl>;
1199
1200
using FunctionBitmapToString = FunctionUnaryToType<BitmapToString, NameBitmapToString>;
1201
using FunctionBitmapToBase64 = FunctionUnaryToType<BitmapToBase64, NameBitmapToBase64>;
1202
using FunctionBitmapFromBase64 = FunctionBitmapAlwaysNull<BitmapFromBase64>;
1203
using FunctionBitmapNot =
1204
        FunctionBinaryToType<DataTypeBitMap, DataTypeBitMap, BitmapNot, NameBitmapNot>;
1205
using FunctionBitmapContains =
1206
        FunctionBinaryToType<DataTypeBitMap, DataTypeInt64, BitmapContains, NameBitmapContains>;
1207
using FunctionBitmapRemove =
1208
        FunctionBinaryToType<DataTypeBitMap, DataTypeInt64, BitmapRemove, NameBitmapRemove>;
1209
1210
using FunctionBitmapHasAny =
1211
        FunctionBinaryToType<DataTypeBitMap, DataTypeBitMap, BitmapHasAny, NameBitmapHasAny>;
1212
using FunctionBitmapHasAll =
1213
        FunctionBinaryToType<DataTypeBitMap, DataTypeBitMap, BitmapHasAll, NameBitmapHasAll>;
1214
using FunctionSubBitmap = FunctionBitmapSubs<SubBitmap>;
1215
using FunctionBitmapSubsetLimit = FunctionBitmapSubs<BitmapSubsetLimit>;
1216
using FunctionBitmapSubsetInRange = FunctionBitmapSubs<BitmapSubsetInRange>;
1217
1218
8
void register_function_bitmap(SimpleFunctionFactory& factory) {
1219
8
    factory.register_function<FunctionBitmapEmpty>();
1220
8
    factory.register_function<FunctionToBitmap>();
1221
8
    factory.register_function<FunctionToBitmapWithCheck>();
1222
8
    factory.register_function<FunctionBitmapFromString>();
1223
8
    factory.register_function<FunctionBitmapToBase64>();
1224
8
    factory.register_function<FunctionBitmapFromBase64>();
1225
8
    factory.register_function<FunctionBitmapFromArray>();
1226
8
    factory.register_function<FunctionBitmapHash>();
1227
8
    factory.register_function<FunctionBitmapHash64>();
1228
8
    factory.register_function<FunctionBitmapCount>();
1229
8
    factory.register_function<FunctionBitmapMin>();
1230
8
    factory.register_function<FunctionBitmapMax>();
1231
8
    factory.register_function<FunctionBitmapToString>();
1232
8
    factory.register_function<FunctionBitmapNot>();
1233
8
    factory.register_alias(NameBitmapNot::name, "bitmap_and_not");
1234
8
    factory.register_alias(NameBitmapNot::name, "bitmap_andnot");
1235
8
    factory.register_function<FunctionBitmapAndNotCount<NameBitmapAndNotCount>>();
1236
8
    factory.register_function<FunctionBitmapAndNotCount<NameBitmapAndNotCount, true>>();
1237
8
    factory.register_alias(NameBitmapAndNotCount::name, "bitmap_andnot_count");
1238
8
    factory.register_function<FunctionBitmapContains>();
1239
8
    factory.register_function<FunctionBitmapRemove>();
1240
8
    factory.register_function<FunctionBitmapHasAny>();
1241
8
    factory.register_function<FunctionBitmapHasAll>();
1242
8
    factory.register_function<FunctionSubBitmap>();
1243
8
    factory.register_function<FunctionBitmapSubsetLimit>();
1244
8
    factory.register_function<FunctionBitmapSubsetInRange>();
1245
8
    factory.register_function<FunctionBitmapToArray>();
1246
8
}
1247
1248
} // namespace doris