Coverage Report

Created: 2024-11-21 14:31

/var/local/thirdparty/installed/include/roaring/array_util.h
Line
Count
Source (jump to first uncovered line)
1
#ifndef ARRAY_UTIL_H
2
#define ARRAY_UTIL_H
3
4
#include <stddef.h>  // for size_t
5
#include <stdint.h>
6
7
#include <roaring/portability.h>
8
9
#if CROARING_IS_X64
10
#ifndef CROARING_COMPILER_SUPPORTS_AVX512
11
#error "CROARING_COMPILER_SUPPORTS_AVX512 needs to be defined."
12
#endif // CROARING_COMPILER_SUPPORTS_AVX512
13
#endif
14
15
#ifdef __cplusplus
16
extern "C" { namespace roaring { namespace internal {
17
#endif
18
19
/*
20
 *  Good old binary search.
21
 *  Assumes that array is sorted, has logarithmic complexity.
22
 *  if the result is x, then:
23
 *     if ( x>0 )  you have array[x] = ikey
24
 *     if ( x<0 ) then inserting ikey at position -x-1 in array (insuring that array[-x-1]=ikey)
25
 *                   keys the array sorted.
26
 */
27
inline int32_t binarySearch(const uint16_t *array, int32_t lenarray,
28
0
                            uint16_t ikey) {
29
0
    int32_t low = 0;
30
0
    int32_t high = lenarray - 1;
31
0
    while (low <= high) {
32
0
        int32_t middleIndex = (low + high) >> 1;
33
0
        uint16_t middleValue = array[middleIndex];
34
0
        if (middleValue < ikey) {
35
0
            low = middleIndex + 1;
36
0
        } else if (middleValue > ikey) {
37
0
            high = middleIndex - 1;
38
0
        } else {
39
0
            return middleIndex;
40
0
        }
41
0
    }
42
0
    return -(low + 1);
43
0
}
44
45
/**
46
 * Galloping search
47
 * Assumes that array is sorted, has logarithmic complexity.
48
 * if the result is x, then if x = length, you have that all values in array between pos and length
49
 *    are smaller than min.
50
 * otherwise returns the first index x such that array[x] >= min.
51
 */
52
static inline int32_t advanceUntil(const uint16_t *array, int32_t pos,
53
0
                                   int32_t length, uint16_t min) {
54
0
    int32_t lower = pos + 1;
55
0
56
0
    if ((lower >= length) || (array[lower] >= min)) {
57
0
        return lower;
58
0
    }
59
0
60
0
    int32_t spansize = 1;
61
0
62
0
    while ((lower + spansize < length) && (array[lower + spansize] < min)) {
63
0
        spansize <<= 1;
64
0
    }
65
0
    int32_t upper = (lower + spansize < length) ? lower + spansize : length - 1;
66
0
67
0
    if (array[upper] == min) {
68
0
        return upper;
69
0
    }
70
0
    if (array[upper] < min) {
71
0
        // means
72
0
        // array
73
0
        // has no
74
0
        // item
75
0
        // >= min
76
0
        // pos = array.length;
77
0
        return length;
78
0
    }
79
0
80
0
    // we know that the next-smallest span was too small
81
0
    lower += (spansize >> 1);
82
0
83
0
    int32_t mid = 0;
84
0
    while (lower + 1 != upper) {
85
0
        mid = (lower + upper) >> 1;
86
0
        if (array[mid] == min) {
87
0
            return mid;
88
0
        } else if (array[mid] < min) {
89
0
            lower = mid;
90
0
        } else {
91
0
            upper = mid;
92
0
        }
93
0
    }
94
0
    return upper;
95
0
}
Unexecuted instantiation: bkd_writer.cpp:_ZN7roaring8internalL12advanceUntilEPKtiit
Unexecuted instantiation: bkd_reader.cpp:_ZN7roaring8internalL12advanceUntilEPKtiit
Unexecuted instantiation: packed_index_tree.cpp:_ZN7roaring8internalL12advanceUntilEPKtiit
Unexecuted instantiation: index_tree.cpp:_ZN7roaring8internalL12advanceUntilEPKtiit
Unexecuted instantiation: legacy_index_tree.cpp:_ZN7roaring8internalL12advanceUntilEPKtiit
Unexecuted instantiation: docids_writer.cpp:_ZN7roaring8internalL12advanceUntilEPKtiit
Unexecuted instantiation: IndexWriter.cpp:_ZN7roaring8internalL12advanceUntilEPKtiit
96
97
/**
98
 * Returns number of elements which are less than ikey.
99
 * Array elements must be unique and sorted.
100
 */
101
static inline int32_t count_less(const uint16_t *array, int32_t lenarray,
102
0
                                 uint16_t ikey) {
103
0
    if (lenarray == 0) return 0;
104
0
    int32_t pos = binarySearch(array, lenarray, ikey);
105
0
    return pos >= 0 ? pos : -(pos+1);
106
0
}
Unexecuted instantiation: bkd_writer.cpp:_ZN7roaring8internalL10count_lessEPKtit
Unexecuted instantiation: bkd_reader.cpp:_ZN7roaring8internalL10count_lessEPKtit
Unexecuted instantiation: packed_index_tree.cpp:_ZN7roaring8internalL10count_lessEPKtit
Unexecuted instantiation: index_tree.cpp:_ZN7roaring8internalL10count_lessEPKtit
Unexecuted instantiation: legacy_index_tree.cpp:_ZN7roaring8internalL10count_lessEPKtit
Unexecuted instantiation: docids_writer.cpp:_ZN7roaring8internalL10count_lessEPKtit
Unexecuted instantiation: IndexWriter.cpp:_ZN7roaring8internalL10count_lessEPKtit
107
108
/**
109
 * Returns number of elements which are greater than ikey.
110
 * Array elements must be unique and sorted.
111
 */
112
static inline int32_t count_greater(const uint16_t *array, int32_t lenarray,
113
0
                                    uint16_t ikey) {
114
0
    if (lenarray == 0) return 0;
115
0
    int32_t pos = binarySearch(array, lenarray, ikey);
116
0
    if (pos >= 0) {
117
0
        return lenarray - (pos+1);
118
0
    } else {
119
0
        return lenarray - (-pos-1);
120
0
    }
121
0
}
Unexecuted instantiation: bkd_writer.cpp:_ZN7roaring8internalL13count_greaterEPKtit
Unexecuted instantiation: bkd_reader.cpp:_ZN7roaring8internalL13count_greaterEPKtit
Unexecuted instantiation: packed_index_tree.cpp:_ZN7roaring8internalL13count_greaterEPKtit
Unexecuted instantiation: index_tree.cpp:_ZN7roaring8internalL13count_greaterEPKtit
Unexecuted instantiation: legacy_index_tree.cpp:_ZN7roaring8internalL13count_greaterEPKtit
Unexecuted instantiation: docids_writer.cpp:_ZN7roaring8internalL13count_greaterEPKtit
Unexecuted instantiation: IndexWriter.cpp:_ZN7roaring8internalL13count_greaterEPKtit
122
123
/**
124
 * From Schlegel et al., Fast Sorted-Set Intersection using SIMD Instructions
125
 * Optimized by D. Lemire on May 3rd 2013
126
 *
127
 * C should have capacity greater than the minimum of s_1 and s_b + 8
128
 * where 8 is sizeof(__m128i)/sizeof(uint16_t).
129
 */
130
int32_t intersect_vector16(const uint16_t *__restrict__ A, size_t s_a,
131
                           const uint16_t *__restrict__ B, size_t s_b,
132
                           uint16_t *C);
133
134
int32_t intersect_vector16_inplace(uint16_t *__restrict__ A, size_t s_a,
135
                           const uint16_t *__restrict__ B, size_t s_b);
136
137
/**
138
 * Take an array container and write it out to a 32-bit array, using base
139
 * as the offset.
140
 */
141
int array_container_to_uint32_array_vector16(void *vout, const uint16_t* array, size_t cardinality,
142
                                    uint32_t base);
143
#if CROARING_COMPILER_SUPPORTS_AVX512
144
int avx512_array_container_to_uint32_array(void *vout, const uint16_t* array, size_t cardinality,
145
                                    uint32_t base);
146
#endif
147
/**
148
 * Compute the cardinality of the intersection using SSE4 instructions
149
 */
150
int32_t intersect_vector16_cardinality(const uint16_t *__restrict__ A,
151
                                       size_t s_a,
152
                                       const uint16_t *__restrict__ B,
153
                                       size_t s_b);
154
155
/* Computes the intersection between one small and one large set of uint16_t.
156
 * Stores the result into buffer and return the number of elements. */
157
int32_t intersect_skewed_uint16(const uint16_t *smallarray, size_t size_s,
158
                                const uint16_t *largearray, size_t size_l,
159
                                uint16_t *buffer);
160
161
/* Computes the size of the intersection between one small and one large set of
162
 * uint16_t. */
163
int32_t intersect_skewed_uint16_cardinality(const uint16_t *smallarray,
164
                                            size_t size_s,
165
                                            const uint16_t *largearray,
166
                                            size_t size_l);
167
168
169
/* Check whether the size of the intersection between one small and one large set of uint16_t is non-zero. */
170
bool intersect_skewed_uint16_nonempty(const uint16_t *smallarray, size_t size_s,
171
                                const uint16_t *largearray, size_t size_l);
172
/**
173
 * Generic intersection function.
174
 */
175
int32_t intersect_uint16(const uint16_t *A, const size_t lenA,
176
                         const uint16_t *B, const size_t lenB, uint16_t *out);
177
/**
178
 * Compute the size of the intersection (generic).
179
 */
180
int32_t intersect_uint16_cardinality(const uint16_t *A, const size_t lenA,
181
                                     const uint16_t *B, const size_t lenB);
182
183
/**
184
 * Checking whether the size of the intersection  is non-zero.
185
 */
186
bool intersect_uint16_nonempty(const uint16_t *A, const size_t lenA,
187
                         const uint16_t *B, const size_t lenB);
188
/**
189
 * Generic union function.
190
 */
191
size_t union_uint16(const uint16_t *set_1, size_t size_1, const uint16_t *set_2,
192
                    size_t size_2, uint16_t *buffer);
193
194
/**
195
 * Generic XOR function.
196
 */
197
int32_t xor_uint16(const uint16_t *array_1, int32_t card_1,
198
                   const uint16_t *array_2, int32_t card_2, uint16_t *out);
199
200
/**
201
 * Generic difference function (ANDNOT).
202
 */
203
int difference_uint16(const uint16_t *a1, int length1, const uint16_t *a2,
204
                      int length2, uint16_t *a_out);
205
206
/**
207
 * Generic intersection function.
208
 */
209
size_t intersection_uint32(const uint32_t *A, const size_t lenA,
210
                           const uint32_t *B, const size_t lenB, uint32_t *out);
211
212
/**
213
 * Generic intersection function, returns just the cardinality.
214
 */
215
size_t intersection_uint32_card(const uint32_t *A, const size_t lenA,
216
                                const uint32_t *B, const size_t lenB);
217
218
/**
219
 * Generic union function.
220
 */
221
size_t union_uint32(const uint32_t *set_1, size_t size_1, const uint32_t *set_2,
222
                    size_t size_2, uint32_t *buffer);
223
224
/**
225
 * A fast SSE-based union function.
226
 */
227
uint32_t union_vector16(const uint16_t *__restrict__ set_1, uint32_t size_1,
228
                        const uint16_t *__restrict__ set_2, uint32_t size_2,
229
                        uint16_t *__restrict__ buffer);
230
/**
231
 * A fast SSE-based XOR function.
232
 */
233
uint32_t xor_vector16(const uint16_t *__restrict__ array1, uint32_t length1,
234
                      const uint16_t *__restrict__ array2, uint32_t length2,
235
                      uint16_t *__restrict__ output);
236
237
/**
238
 * A fast SSE-based difference function.
239
 */
240
int32_t difference_vector16(const uint16_t *__restrict__ A, size_t s_a,
241
                            const uint16_t *__restrict__ B, size_t s_b,
242
                            uint16_t *C);
243
244
/**
245
 * Generic union function, returns just the cardinality.
246
 */
247
size_t union_uint32_card(const uint32_t *set_1, size_t size_1,
248
                         const uint32_t *set_2, size_t size_2);
249
250
/**
251
* combines union_uint16 and  union_vector16 optimally
252
*/
253
size_t fast_union_uint16(const uint16_t *set_1, size_t size_1, const uint16_t *set_2,
254
                    size_t size_2, uint16_t *buffer);
255
256
257
bool memequals(const void *s1, const void *s2, size_t n);
258
259
#ifdef __cplusplus
260
} } }  // extern "C" { namespace roaring { namespace internal {
261
#endif
262
263
#endif