aerospike 2.24.0 → 2.26.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/CHANGELOG.md +27 -0
- data/lib/aerospike/cdt/context.rb +136 -69
- data/lib/aerospike/cdt/map_policy.rb +16 -2
- data/lib/aerospike/cdt/map_return_type.rb +9 -1
- data/lib/aerospike/client.rb +30 -32
- data/lib/aerospike/command/command.rb +104 -98
- data/lib/aerospike/command/operate_args.rb +99 -0
- data/lib/aerospike/command/operate_command.rb +6 -11
- data/lib/aerospike/exp/exp.rb +401 -334
- data/lib/aerospike/exp/exp_bit.rb +388 -0
- data/lib/aerospike/exp/exp_hll.rb +169 -0
- data/lib/aerospike/exp/exp_list.rb +403 -0
- data/lib/aerospike/exp/exp_map.rb +493 -0
- data/lib/aerospike/exp/operation.rb +56 -0
- data/lib/aerospike/features.rb +13 -0
- data/lib/aerospike/operation.rb +20 -22
- data/lib/aerospike/policy/policy.rb +25 -12
- data/lib/aerospike/query/filter.rb +44 -32
- data/lib/aerospike/query/query_executor.rb +7 -9
- data/lib/aerospike/query/query_partition_command.rb +32 -31
- data/lib/aerospike/query/recordset.rb +9 -9
- data/lib/aerospike/query/scan_executor.rb +7 -5
- data/lib/aerospike/task/execute_task.rb +17 -14
- data/lib/aerospike/utils/buffer.rb +46 -38
- data/lib/aerospike/utils/packer.rb +7 -6
- data/lib/aerospike/value/value.rb +21 -51
- data/lib/aerospike/version.rb +1 -1
- data/lib/aerospike.rb +156 -148
- metadata +8 -2
@@ -0,0 +1,388 @@
|
|
1
|
+
# encoding: utf-8
|
2
|
+
# Copyright 2014-2022 Aerospike, Inc.
|
3
|
+
#
|
4
|
+
# Portions may be licensed to Aerospike, Inc. under one or more contributor
|
5
|
+
# license agreements.
|
6
|
+
#
|
7
|
+
# Licensed under the Apache License, Version 2.0 (the "License"); you may no
|
8
|
+
# use this file except in compliance with the License. You may obtain a copy of
|
9
|
+
# the License at http:#www.apache.org/licenses/LICENSE-2.0
|
10
|
+
#
|
11
|
+
# Unless required by applicable law or agreed to in writing, software
|
12
|
+
# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
|
13
|
+
# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
|
14
|
+
# License for the specific language governing permissions and limitations under
|
15
|
+
# the License.
|
16
|
+
|
17
|
+
module Aerospike
|
18
|
+
# Bit expression generator. See {@link Exp}.
|
19
|
+
#
|
20
|
+
# The bin expression argument in these methods can be a reference to a bin or the
|
21
|
+
# result of another expression. Expressions that modify bin values are only used
|
22
|
+
# for temporary expression evaluation and are not permanently applied to the bin.
|
23
|
+
# Bit modify expressions the blob bin's value.
|
24
|
+
#
|
25
|
+
# Offset orientation is left-to-right. Negative offsets are supported.
|
26
|
+
# If the offset is negative, the offset starts backwards from end of the bitmap.
|
27
|
+
# If an offset is out of bounds, a parameter error will be returned.
|
28
|
+
class Exp::Bit
|
29
|
+
# Create expression that resizes _byte[]_ to _byte_size_ according to _resize_flags_ (See {CDT::BitResizeFlags})
|
30
|
+
# and returns byte[].
|
31
|
+
#
|
32
|
+
# bin = [0b00000001, 0b01000010]
|
33
|
+
# byte_size = 4
|
34
|
+
# resize_flags = 0
|
35
|
+
# returns [0b00000001, 0b01000010, 0b00000000, 0b00000000]
|
36
|
+
#
|
37
|
+
# ==== Examples
|
38
|
+
# # Resize bin "a" and compare bit count
|
39
|
+
# Exp.eq(
|
40
|
+
# BitExp.count(Exp.val(0), Exp.val(3),
|
41
|
+
# BitExp.resize(BitPolicy.Default, Exp.val(4), 0, Exp.blobBin("a"))),
|
42
|
+
# Exp.val(2))
|
43
|
+
def self.resize(byte_size, resize_flags, bin, policy: CDT::BitPolicy::DEFAULT)
|
44
|
+
bytes = Exp.pack(nil, RESIZE, byte_size, policy.flags, resize_flags)
|
45
|
+
self.add_write(bin, bytes)
|
46
|
+
end
|
47
|
+
|
48
|
+
# Create expression that inserts value bytes into byte[] bin at byte_offset and returns byte[].
|
49
|
+
#
|
50
|
+
# bin = [0b00000001, 0b01000010, 0b00000011, 0b00000100, 0b00000101]
|
51
|
+
# byte_offset = 1
|
52
|
+
# value = [0b11111111, 0b11000111]
|
53
|
+
# bin result = [0b00000001, 0b11111111, 0b11000111, 0b01000010, 0b00000011, 0b00000100, 0b00000101]
|
54
|
+
#
|
55
|
+
# ==== Examples
|
56
|
+
# # Insert bytes into bin "a" and compare bit count
|
57
|
+
# Exp.eq(
|
58
|
+
# BitExp.count(Exp.val(0), Exp.val(3),
|
59
|
+
# BitExp.insert(BitPolicy.Default, Exp.val(1), Exp.val(bytes), Exp.blobBin("a"))),
|
60
|
+
# Exp.val(2))
|
61
|
+
def self.insert(byte_offset, value, bin, policy: CDT::BitPolicy::DEFAULT)
|
62
|
+
bytes = Exp.pack(nil, INSERT, byte_offset, value, policy.flags)
|
63
|
+
self.add_write(bin, bytes)
|
64
|
+
end
|
65
|
+
|
66
|
+
# Create expression that removes bytes from byte[] bin at byte_offset for byte_size and returns byte[].
|
67
|
+
#
|
68
|
+
# bin = [0b00000001, 0b01000010, 0b00000011, 0b00000100, 0b00000101]
|
69
|
+
# byte_offset = 2
|
70
|
+
# byte_size = 3
|
71
|
+
# bin result = [0b00000001, 0b01000010]
|
72
|
+
#
|
73
|
+
# ==== Examples
|
74
|
+
# # Remove bytes from bin "a" and compare bit count
|
75
|
+
# Exp.eq(
|
76
|
+
# BitExp.count(Exp.val(0), Exp.val(3),
|
77
|
+
# BitExp.remove(BitPolicy.Default, Exp.val(2), Exp.val(3), Exp.blobBin("a"))),
|
78
|
+
# Exp.val(2))
|
79
|
+
def self.remove(byte_offset, byte_size, bin, policy: CDT::BitPolicy::DEFAULT)
|
80
|
+
bytes = Exp.pack(nil, REMOVE, byte_offset, byte_size, policy.flags)
|
81
|
+
self.add_write(bin, bytes)
|
82
|
+
end
|
83
|
+
|
84
|
+
# Create expression that sets value on byte[] bin at bit_offset for bit_size and returns byte[].
|
85
|
+
#
|
86
|
+
# bin = [0b00000001, 0b01000010, 0b00000011, 0b00000100, 0b00000101]
|
87
|
+
# bit_offset = 13
|
88
|
+
# bit_size = 3
|
89
|
+
# value = [0b11100000]
|
90
|
+
# bin result = [0b00000001, 0b01000111, 0b00000011, 0b00000100, 0b00000101]
|
91
|
+
#
|
92
|
+
# ==== Examples
|
93
|
+
# # Set bytes in bin "a" and compare bit count
|
94
|
+
# Exp.eq(
|
95
|
+
# BitExp.count(Exp.val(0), Exp.val(3),
|
96
|
+
# BitExp.set(BitPolicy.Default, Exp.val(13), Exp.val(3), Exp.val(bytes), Exp.blobBin("a"))),
|
97
|
+
# Exp.val(2))
|
98
|
+
def self.set(bit_offset, bit_size, value, bin, policy: CDT::BitPolicy::DEFAULT)
|
99
|
+
bytes = Exp.pack(nil, SET, bit_offset, bit_size, value, policy.flags)
|
100
|
+
self.add_write(bin, bytes)
|
101
|
+
end
|
102
|
+
|
103
|
+
# Create expression that performs bitwise "or" on value and byte[] bin at bit_offset for bit_size
|
104
|
+
# and returns byte[].
|
105
|
+
#
|
106
|
+
# bin = [0b00000001, 0b01000010, 0b00000011, 0b00000100, 0b00000101]
|
107
|
+
# bit_offset = 17
|
108
|
+
# bit_size = 6
|
109
|
+
# value = [0b10101000]
|
110
|
+
# bin result = [0b00000001, 0b01000010, 0b01010111, 0b00000100, 0b00000101]
|
111
|
+
#
|
112
|
+
def self.or(bit_offset, bit_size, value, bin, policy: CDT::BitPolicy::DEFAULT)
|
113
|
+
bytes = Exp.pack(nil, OR, bit_offset, bit_size, value, policy.flags)
|
114
|
+
self.add_write(bin, bytes)
|
115
|
+
end
|
116
|
+
|
117
|
+
# Create expression that performs bitwise "xor" on value and byte[] bin at bit_offset for bit_size
|
118
|
+
# and returns byte[].
|
119
|
+
#
|
120
|
+
# bin = [0b00000001, 0b01000010, 0b00000011, 0b00000100, 0b00000101]
|
121
|
+
# bit_offset = 17
|
122
|
+
# bit_size = 6
|
123
|
+
# value = [0b10101100]
|
124
|
+
# bin result = [0b00000001, 0b01000010, 0b01010101, 0b00000100, 0b00000101]
|
125
|
+
#
|
126
|
+
def self.xor(bit_offset, bit_size, value, bin, policy: CDT::BitPolicy::DEFAULT)
|
127
|
+
bytes = Exp.pack(nil, XOR, bit_offset, bit_size, value, policy.flags)
|
128
|
+
self.add_write(bin, bytes)
|
129
|
+
end
|
130
|
+
|
131
|
+
# Create expression that performs bitwise "and" on value and byte[] bin at bit_offset for bit_size
|
132
|
+
# and returns byte[].
|
133
|
+
#
|
134
|
+
# bin = [0b00000001, 0b01000010, 0b00000011, 0b00000100, 0b00000101]
|
135
|
+
# bit_offset = 23
|
136
|
+
# bit_size = 9
|
137
|
+
# value = [0b00111100, 0b10000000]
|
138
|
+
# bin result = [0b00000001, 0b01000010, 0b00000010, 0b00000000, 0b00000101]
|
139
|
+
#
|
140
|
+
def self.and(bit_offset, bit_size, value, bin, policy: CDT::BitPolicy::DEFAULT)
|
141
|
+
bytes = Exp.pack(nil, AND, bit_offset, bit_size, value, policy.flags)
|
142
|
+
self.add_write(bin, bytes)
|
143
|
+
end
|
144
|
+
|
145
|
+
# Create expression that negates byte[] bin starting at bit_offset for bit_size and returns byte[].
|
146
|
+
#
|
147
|
+
# bin = [0b00000001, 0b01000010, 0b00000011, 0b00000100, 0b00000101]
|
148
|
+
# bit_offset = 25
|
149
|
+
# bit_size = 6
|
150
|
+
# bin result = [0b00000001, 0b01000010, 0b00000011, 0b01111010, 0b00000101]
|
151
|
+
#
|
152
|
+
def self.not(bit_offset, bit_size, bin, policy: CDT::BitPolicy::DEFAULT)
|
153
|
+
bytes = Exp.pack(nil, NOT, bit_offset, bit_size, policy.flags)
|
154
|
+
self.add_write(bin, bytes)
|
155
|
+
end
|
156
|
+
|
157
|
+
# Create expression that shifts left byte[] bin starting at bit_offset for bit_size and returns byte[].
|
158
|
+
#
|
159
|
+
# bin = [0b00000001, 0b01000010, 0b00000011, 0b00000100, 0b00000101]
|
160
|
+
# bit_offset = 32
|
161
|
+
# bit_size = 8
|
162
|
+
# shift = 3
|
163
|
+
# bin result = [0b00000001, 0b01000010, 0b00000011, 0b00000100, 0b00101000]
|
164
|
+
#
|
165
|
+
def self.lshift(bit_offset, bit_size, shift, bin, policy: CDT::BitPolicy::DEFAULT)
|
166
|
+
bytes = Exp.pack(nil, LSHIFT, bit_offset, bit_size, shift, policy.flags)
|
167
|
+
self.add_write(bin, bytes)
|
168
|
+
end
|
169
|
+
|
170
|
+
# Create expression that shifts right byte[] bin starting at bit_offset for bit_size and returns byte[].
|
171
|
+
#
|
172
|
+
# bin = [0b00000001, 0b01000010, 0b00000011, 0b00000100, 0b00000101]
|
173
|
+
# bit_offset = 0
|
174
|
+
# bit_size = 9
|
175
|
+
# shift = 1
|
176
|
+
# bin result = [0b00000000, 0b11000010, 0b00000011, 0b00000100, 0b00000101]
|
177
|
+
#
|
178
|
+
def self.rshift(bit_offset, bit_size, shift, bin, policy: CDT::BitPolicy::DEFAULT)
|
179
|
+
bytes = Exp.pack(nil, RSHIFT, bit_offset, bit_size, shift, policy.flags)
|
180
|
+
self.add_write(bin, bytes)
|
181
|
+
end
|
182
|
+
|
183
|
+
# Create expression that adds value to byte[] bin starting at bit_offset for bit_size and returns byte[].
|
184
|
+
# BitSize must be <= 64. Signed indicates if bits should be treated as a signed number.
|
185
|
+
# If add overflows/underflows, {@link BitOverflowAction} is used.
|
186
|
+
#
|
187
|
+
# bin = [0b00000001, 0b01000010, 0b00000011, 0b00000100, 0b00000101]
|
188
|
+
# bit_offset = 24
|
189
|
+
# bit_size = 16
|
190
|
+
# value = 128
|
191
|
+
# signed = false
|
192
|
+
# bin result = [0b00000001, 0b01000010, 0b00000011, 0b00000100, 0b10000101]
|
193
|
+
#
|
194
|
+
def self.add(bit_offset, bit_size, value, signed, bit_overflow_action, bin, policy: CDT::BitPolicy::DEFAULT)
|
195
|
+
bytes = self.pack_math(ADD, policy, bit_offset, bit_size, value, signed, bit_overflow_action)
|
196
|
+
self.add_write(bin, bytes)
|
197
|
+
end
|
198
|
+
|
199
|
+
# Create expression that subtracts value from byte[] bin starting at bit_offset for bit_size and returns byte[].
|
200
|
+
# BitSize must be <= 64. Signed indicates if bits should be treated as a signed number.
|
201
|
+
# If add overflows/underflows, {@link BitOverflowAction} is used.
|
202
|
+
#
|
203
|
+
# bin = [0b00000001, 0b01000010, 0b00000011, 0b00000100, 0b00000101]
|
204
|
+
# bit_offset = 24
|
205
|
+
# bit_size = 16
|
206
|
+
# value = 128
|
207
|
+
# signed = false
|
208
|
+
# bin result = [0b00000001, 0b01000010, 0b00000011, 0b0000011, 0b10000101]
|
209
|
+
#
|
210
|
+
def self.subtract(bit_offset, bit_size, value, signed, bit_overflow_action, bin, policy: CDT::BitPolicy::DEFAULT)
|
211
|
+
bytes = self.pack_math(SUBTRACT, policy, bit_offset, bit_size, value, signed, bit_overflow_action)
|
212
|
+
self.add_write(bin, bytes)
|
213
|
+
end
|
214
|
+
|
215
|
+
# Create expression that sets value to byte[] bin starting at bit_offset for bit_size and returns byte[].
|
216
|
+
# BitSize must be <= 64.
|
217
|
+
#
|
218
|
+
# bin = [0b00000001, 0b01000010, 0b00000011, 0b00000100, 0b00000101]
|
219
|
+
# bit_offset = 1
|
220
|
+
# bit_size = 8
|
221
|
+
# value = 127
|
222
|
+
# bin result = [0b00111111, 0b11000010, 0b00000011, 0b0000100, 0b00000101]
|
223
|
+
#
|
224
|
+
def self.set_int(bit_offset, bit_size, value, bin, policy: CDT::BitPolicy::DEFAULT)
|
225
|
+
bytes = Exp.pack(nil, SET_INT, bit_offset, bit_size, value, policy.flags)
|
226
|
+
self.add_write(bin, bytes)
|
227
|
+
end
|
228
|
+
|
229
|
+
# Create expression that returns bits from byte[] bin starting at bit_offset for bit_size.
|
230
|
+
#
|
231
|
+
# bin = [0b00000001, 0b01000010, 0b00000011, 0b00000100, 0b00000101]
|
232
|
+
# bit_offset = 9
|
233
|
+
# bit_size = 5
|
234
|
+
# returns [0b10000000]
|
235
|
+
#
|
236
|
+
# ==== Examples
|
237
|
+
# # Bin "a" bits = [0b10000000]
|
238
|
+
# Exp.eq(
|
239
|
+
# BitExp.get(Exp.val(9), Exp.val(5), Exp.blobBin("a")),
|
240
|
+
# Exp.val(new byte[] {(byte)0b10000000}))
|
241
|
+
def self.get(bit_offset, bit_size, bin)
|
242
|
+
bytes = Exp.pack(nil, GET, bit_offset, bit_size)
|
243
|
+
self.add_read(bin, bytes, Exp::Type::BLOB)
|
244
|
+
end
|
245
|
+
|
246
|
+
# Create expression that returns integer count of set bits from byte[] bin starting at
|
247
|
+
# bit_offset for bit_size.
|
248
|
+
#
|
249
|
+
# bin = [0b00000001, 0b01000010, 0b00000011, 0b00000100, 0b00000101]
|
250
|
+
# bit_offset = 20
|
251
|
+
# bit_size = 4
|
252
|
+
# returns 2
|
253
|
+
#
|
254
|
+
# ==== Examples
|
255
|
+
# # Bin "a" bit count <= 2
|
256
|
+
# Exp.le(BitExp.count(Exp.val(0), Exp.val(5), Exp.blobBin("a")), Exp.val(2))
|
257
|
+
def self.count(bit_offset, bit_size, bin)
|
258
|
+
bytes = Exp.pack(nil, COUNT, bit_offset, bit_size)
|
259
|
+
self.add_read(bin, bytes, Exp::Type::INT)
|
260
|
+
end
|
261
|
+
|
262
|
+
# Create expression that returns integer bit offset of the first specified value bit in byte[] bin
|
263
|
+
# starting at bit_offset for bit_size.
|
264
|
+
#
|
265
|
+
# bin = [0b00000001, 0b01000010, 0b00000011, 0b00000100, 0b00000101]
|
266
|
+
# bit_offset = 24
|
267
|
+
# bit_size = 8
|
268
|
+
# value = true
|
269
|
+
# returns 5
|
270
|
+
#
|
271
|
+
# ==== Examples
|
272
|
+
# # lscan(a) == 5
|
273
|
+
# Exp.eq(BitExp.lscan(Exp.val(24), Exp.val(8), Exp.val(true), Exp.blobBin("a")), Exp.val(5))
|
274
|
+
#
|
275
|
+
# @param bit_offset offset int expression
|
276
|
+
# @param bit_size size int expression
|
277
|
+
# @param value boolean expression
|
278
|
+
# @param bin bin or blob value expression
|
279
|
+
def self.lscan(bit_offset, bit_size, value, bin)
|
280
|
+
bytes = Exp.pack(nil, LSCAN, bit_offset, bit_size, value)
|
281
|
+
self.add_read(bin, bytes, Exp::Type::INT)
|
282
|
+
end
|
283
|
+
|
284
|
+
# Create expression that returns integer bit offset of the last specified value bit in byte[] bin
|
285
|
+
# starting at bit_offset for bit_size.
|
286
|
+
# Example:
|
287
|
+
#
|
288
|
+
# bin = [0b00000001, 0b01000010, 0b00000011, 0b00000100, 0b00000101]
|
289
|
+
# bit_offset = 32
|
290
|
+
# bit_size = 8
|
291
|
+
# value = true
|
292
|
+
# returns 7
|
293
|
+
#
|
294
|
+
# ==== Examples
|
295
|
+
# # rscan(a) == 7
|
296
|
+
# Exp.eq(BitExp.rscan(Exp.val(32), Exp.val(8), Exp.val(true), Exp.blobBin("a")), Exp.val(7))
|
297
|
+
#
|
298
|
+
# @param bit_offset offset int expression
|
299
|
+
# @param bit_size size int expression
|
300
|
+
# @param value boolean expression
|
301
|
+
# @param bin bin or blob value expression
|
302
|
+
def self.rscan(bit_offset, bit_size, value, bin)
|
303
|
+
bytes = Exp.pack(nil, RSCAN, bit_offset, bit_size, value)
|
304
|
+
self.add_read(bin, bytes, Exp::Type::INT)
|
305
|
+
end
|
306
|
+
|
307
|
+
# Create expression that returns integer from byte[] bin starting at bit_offset for bit_size.
|
308
|
+
# Signed indicates if bits should be treated as a signed number.
|
309
|
+
#
|
310
|
+
# bin = [0b00000001, 0b01000010, 0b00000011, 0b00000100, 0b00000101]
|
311
|
+
# bit_offset = 8
|
312
|
+
# bit_size = 16
|
313
|
+
# signed = false
|
314
|
+
# returns 16899
|
315
|
+
#
|
316
|
+
# ==== Examples
|
317
|
+
# # getInt(a) == 16899
|
318
|
+
# Exp.eq(BitExp.getInt(Exp.val(8), Exp.val(16), false, Exp.blobBin("a")), Exp.val(16899))
|
319
|
+
def self.get_int(bit_offset, bit_size, signed, bin)
|
320
|
+
bytes = self.pack_get_int(bit_offset, bit_size, signed)
|
321
|
+
self.add_read(bin, bytes, Exp::Type::INT)
|
322
|
+
end
|
323
|
+
|
324
|
+
private
|
325
|
+
|
326
|
+
MODULE = 1
|
327
|
+
RESIZE = 0
|
328
|
+
INSERT = 1
|
329
|
+
REMOVE = 2
|
330
|
+
SET = 3
|
331
|
+
OR = 4
|
332
|
+
XOR = 5
|
333
|
+
AND = 6
|
334
|
+
NOT = 7
|
335
|
+
LSHIFT = 8
|
336
|
+
RSHIFT = 9
|
337
|
+
ADD = 10
|
338
|
+
SUBTRACT = 11
|
339
|
+
SET_INT = 12
|
340
|
+
GET = 50
|
341
|
+
COUNT = 51
|
342
|
+
LSCAN = 52
|
343
|
+
RSCAN = 53
|
344
|
+
GET_INT = 54
|
345
|
+
|
346
|
+
INT_FLAGS_SIGNED = 1
|
347
|
+
|
348
|
+
def self.pack_math(command, policy, bit_offset, bit_size, value, signed, bit_overflow_action)
|
349
|
+
Packer.use do |packer|
|
350
|
+
# Pack.init only required when CTX is used and server does not support CTX for bit operations.
|
351
|
+
# Pack.init(packer, ctx)
|
352
|
+
packer.write_array_header(6)
|
353
|
+
packer.write(command)
|
354
|
+
bit_offset.pack(packer)
|
355
|
+
bit_size.pack(packer)
|
356
|
+
value.pack(packer)
|
357
|
+
packer.write(policy.flags)
|
358
|
+
|
359
|
+
flags = bit_overflow_action
|
360
|
+
flags |= INT_FLAGS_SIGNED if signed
|
361
|
+
|
362
|
+
packer.write(flags)
|
363
|
+
return packer.bytes
|
364
|
+
end
|
365
|
+
end
|
366
|
+
|
367
|
+
def self.pack_get_int(bit_offset, bit_size, signed)
|
368
|
+
Packer.use do |packer|
|
369
|
+
# Pack.init only required when CTX is used and server does not support CTX for bit operations.
|
370
|
+
# Pack.init(packer, ctx)
|
371
|
+
packer.write_array_header(signed ? 4 : 3)
|
372
|
+
packer.write(GET_INT)
|
373
|
+
bit_offset.pack(packer)
|
374
|
+
bit_size.pack(packer)
|
375
|
+
packer.write(INT_FLAGS_SIGNED) if signed
|
376
|
+
return packer.bytes
|
377
|
+
end
|
378
|
+
end
|
379
|
+
|
380
|
+
def self.add_write(bin, bytes)
|
381
|
+
Exp::Module.new(bin, bytes, Exp::Type::BLOB, MODULE | Exp::MODIFY)
|
382
|
+
end
|
383
|
+
|
384
|
+
def self.add_read(bin, bytes, ret_type)
|
385
|
+
Exp::Module.new(bin, bytes, ret_type, MODULE)
|
386
|
+
end
|
387
|
+
end # class
|
388
|
+
end # module
|
@@ -0,0 +1,169 @@
|
|
1
|
+
# encoding: utf-8
|
2
|
+
# Copyright 2014-2022 Aerospike, Inc.
|
3
|
+
#
|
4
|
+
# Portions may be licensed to Aerospike, Inc. under one or more contributor
|
5
|
+
# license agreements.
|
6
|
+
#
|
7
|
+
# Licensed under the Apache License, Version 2.0 (the "License") you may no
|
8
|
+
# use this file except in compliance with the License. You may obtain a copy of
|
9
|
+
# the License at http:#www.apache.org/licenses/LICENSE-2.0
|
10
|
+
#
|
11
|
+
# Unless required by applicable law or agreed to in writing, software
|
12
|
+
# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
|
13
|
+
# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
|
14
|
+
# License for the specific language governing permissions and limitations under
|
15
|
+
# the License.
|
16
|
+
|
17
|
+
module Aerospike
|
18
|
+
# HyperLogLog (HLL) expression generator. See {@link Exp}.
|
19
|
+
#
|
20
|
+
# The bin expression argument in these methods can be a reference to a bin or the
|
21
|
+
# result of another expression. Expressions that modify bin values are only used
|
22
|
+
# for temporary expression evaluation and are not permanently applied to the bin.
|
23
|
+
# HLL modify expressions return the HLL bin's value.
|
24
|
+
class Exp::HLL
|
25
|
+
|
26
|
+
# Create expression that creates a new HLL or resets an existing HLL with minhash bits.
|
27
|
+
#
|
28
|
+
# @param policy write policy, use {@link HLLPolicy#Default} for default
|
29
|
+
# @param index_bit_count number of index bits. Must be between 4 and 16 inclusive.
|
30
|
+
# @param min_hash_bit_count number of min hash bits. Must be between 4 and 51 inclusive.
|
31
|
+
# Also, index_bit_count + min_hash_bit_count must be <= 64. Optional.
|
32
|
+
# @param bin HLL bin or value expression
|
33
|
+
def self.init(index_bit_count, bin, min_hash_bit_count: Exp.int_val(-1), policy: CDT::HLLPolicy::DEFAULT)
|
34
|
+
bytes = Exp.pack(nil, INIT, index_bit_count, min_hash_bit_count, policy.flags)
|
35
|
+
self.add_write(bin, bytes)
|
36
|
+
end
|
37
|
+
|
38
|
+
# Create expression that adds values to a HLL set and returns HLL set. If HLL bin does not
|
39
|
+
# exist, use index_bit_count and min_hash_bit_count to create HLL set.
|
40
|
+
#
|
41
|
+
# ==== Examples
|
42
|
+
# # Add values to HLL bin "a" and check count > 7
|
43
|
+
# Exp.gt(
|
44
|
+
# HLLExp.getCount(
|
45
|
+
# HLLExp.add(HLLPolicy.Default, Exp.val(list), Exp.val(10), Exp.val(20), Exp.hllBin("a"))),
|
46
|
+
# Exp.val(7))
|
47
|
+
#
|
48
|
+
# @param policy write policy, use {@link HLLPolicy#Default} for default
|
49
|
+
# @param list list bin or value expression of values to be added
|
50
|
+
# @param index_bit_count number of index bits expression. Must be between 4 and 16 inclusive.
|
51
|
+
# @param min_hash_bit_count number of min hash bits expression. Must be between 4 and 51 inclusive.
|
52
|
+
# Also, index_bit_count + min_hash_bit_count must be <= 64.
|
53
|
+
# @param bin HLL bin or value expression
|
54
|
+
def self.add(list, bin, policy: CDT::HLLPolicy::DEFAULT, index_bit_count: Exp.val(-1), min_hash_bit_count: Exp.val(-1))
|
55
|
+
bytes = Exp.pack(nil, ADD, list, index_bit_count, min_hash_bit_count, policy.flags)
|
56
|
+
self.add_write(bin, bytes)
|
57
|
+
end
|
58
|
+
|
59
|
+
# Create expression that returns estimated number of elements in the HLL bin.
|
60
|
+
#
|
61
|
+
# ==== Examples
|
62
|
+
# # HLL bin "a" count > 7
|
63
|
+
# Exp.gt(HLLExp.getCount(Exp.hllBin("a")), Exp.val(7))
|
64
|
+
def self.get_count(bin)
|
65
|
+
bytes = Exp.pack(nil, COUNT)
|
66
|
+
self.add_read(bin, bytes, Exp::Type::INT)
|
67
|
+
end
|
68
|
+
|
69
|
+
# Create expression that returns a HLL object that is the union of all specified HLL objects
|
70
|
+
# in the list with the HLL bin.
|
71
|
+
#
|
72
|
+
# ==== Examples
|
73
|
+
# # Union of HLL bins "a" and "b"
|
74
|
+
# HLLExp.getUnion(Exp.hllBin("a"), Exp.hllBin("b"))
|
75
|
+
#
|
76
|
+
# # Union of local HLL list with bin "b"
|
77
|
+
# HLLExp.getUnion(Exp.val(list), Exp.hllBin("b"))
|
78
|
+
def self.get_union(list, bin)
|
79
|
+
bytes = Exp.pack(nil, UNION, list)
|
80
|
+
self.add_read(bin, bytes, Exp::Type::HLL)
|
81
|
+
end
|
82
|
+
|
83
|
+
# Create expression that returns estimated number of elements that would be contained by
|
84
|
+
# the union of these HLL objects.
|
85
|
+
#
|
86
|
+
# ==== Examples
|
87
|
+
# # Union count of HLL bins "a" and "b"
|
88
|
+
# HLLExp.getUnionCount(Exp.hllBin("a"), Exp.hllBin("b"))
|
89
|
+
#
|
90
|
+
# # Union count of local HLL list with bin "b"
|
91
|
+
# HLLExp.getUnionCount(Exp.val(list), Exp.hllBin("b"))
|
92
|
+
def self.get_union_count(list, bin)
|
93
|
+
bytes = Exp.pack(nil, UNION_COUNT, list)
|
94
|
+
self.add_read(bin, bytes, Exp::Type::INT)
|
95
|
+
end
|
96
|
+
|
97
|
+
# Create expression that returns estimated number of elements that would be contained by
|
98
|
+
# the intersection of these HLL objects.
|
99
|
+
#
|
100
|
+
# ==== Examples
|
101
|
+
# # Intersect count of HLL bins "a" and "b"
|
102
|
+
# HLLExp.getIntersectCount(Exp.hllBin("a"), Exp.hllBin("b"))
|
103
|
+
#
|
104
|
+
# # Intersect count of local HLL list with bin "b"
|
105
|
+
# HLLExp.getIntersectCount(Exp.val(list), Exp.hllBin("b"))
|
106
|
+
def self.get_intersect_count(list, bin)
|
107
|
+
bytes = Exp.pack(nil, INTERSECT_COUNT, list)
|
108
|
+
self.add_read(bin, bytes, Exp::Type::INT)
|
109
|
+
end
|
110
|
+
|
111
|
+
# Create expression that returns estimated similarity of these HLL objects as a
|
112
|
+
# 64 bit float.
|
113
|
+
#
|
114
|
+
# ==== Examples
|
115
|
+
# # Similarity of HLL bins "a" and "b" >= 0.75
|
116
|
+
# Exp.ge(HLLExp.getSimilarity(Exp.hllBin("a"), Exp.hllBin("b")), Exp.val(0.75))
|
117
|
+
def self.get_similarity(list, bin)
|
118
|
+
bytes = Exp.pack(nil, SIMILARITY, list)
|
119
|
+
self.add_read(bin, bytes, Exp::Type::FLOAT)
|
120
|
+
end
|
121
|
+
|
122
|
+
# Create expression that returns index_bit_count and min_hash_bit_count used to create HLL bin
|
123
|
+
# in a list of longs. list[0] is index_bit_count and list[1] is min_hash_bit_count.
|
124
|
+
#
|
125
|
+
# ==== Examples
|
126
|
+
# # Bin "a" index_bit_count < 10
|
127
|
+
# Exp.lt(
|
128
|
+
# ListExp.getByIndex(ListReturnType.VALUE, Exp::Type::INT, Exp.val(0),
|
129
|
+
# HLLExp.describe(Exp.hllBin("a"))),
|
130
|
+
# Exp.val(10))
|
131
|
+
def self.describe(bin)
|
132
|
+
bytes = Exp.pack(nil, DESCRIBE)
|
133
|
+
self.add_read(bin, bytes, Exp::Type::LIST)
|
134
|
+
end
|
135
|
+
|
136
|
+
# Create expression that returns one if HLL bin may contain all items in the list.
|
137
|
+
#
|
138
|
+
# ==== Examples
|
139
|
+
# # Bin "a" may contain value "x"
|
140
|
+
# ArrayList<Value> list = new ArrayList<Value>()
|
141
|
+
# list.add(Value.get("x"))
|
142
|
+
# Exp.eq(HLLExp.mayContain(Exp.val(list), Exp.hllBin("a")), Exp.val(1))
|
143
|
+
def self.may_contain(list, bin)
|
144
|
+
bytes = Exp.pack(nil, MAY_CONTAIN, list)
|
145
|
+
self.add_read(bin, bytes, Exp::Type::INT)
|
146
|
+
end
|
147
|
+
|
148
|
+
private
|
149
|
+
|
150
|
+
MODULE = 2
|
151
|
+
INIT = 0
|
152
|
+
ADD = 1
|
153
|
+
COUNT = 50
|
154
|
+
UNION = 51
|
155
|
+
UNION_COUNT = 52
|
156
|
+
INTERSECT_COUNT = 53
|
157
|
+
SIMILARITY = 54
|
158
|
+
DESCRIBE = 55
|
159
|
+
MAY_CONTAIN = 56
|
160
|
+
|
161
|
+
def self.add_write(bin, bytes)
|
162
|
+
Exp::Module.new(bin, bytes, Exp::Type::HLL, MODULE | Exp::MODIFY)
|
163
|
+
end
|
164
|
+
|
165
|
+
def self.add_read(bin, bytes, ret_type)
|
166
|
+
Exp::Module.new(bin, bytes, ret_type, MODULE)
|
167
|
+
end
|
168
|
+
end
|
169
|
+
end
|