nx_sketch_counting_bloom.nx
buildroot/runtime/nx_sketch_counting_bloom.nx
about
sketch_counting_bloom.nx -- Counting Bloom filter (Fan-Cao-Almeida-Broder 1998).
Bloom filter where each "bit" is a c-bit COUNTER instead of a single
bit. Insert increments k counters; delete decrements them. Query
returns "present" iff all k counters > 0.
Compared to other set-membership primitives we ship:
- sketch_bloom (v2): bits only; no delete; smallest memory
- sketch_cuckoo: stores fingerprints in buckets; supports delete;
constant-time lookups; preferred when FPR < 3%
- sketch_counting_bloom (this): COUNTERS not bits; supports delete;
simpler than Cuckoo when FPR matters less;
supports MULTI-SET membership (counter > N tests)
FPR is the same as classic Bloom: (1 - e^(-kn/m))^k. Memory is
k * c times Bloom's (c is counter width in bits).
COUNTER SATURATION: caps at 2^c - 1. Once saturated, subsequent
decrements DO NOT restore the original count (information loss).
We use c=4 (saturation at 15), trading slight FPR overcount risk
for memory.
LOSSLESS-LANGUAGE DISCIPLINE:
nx_cbloom_query returns ApproxI64 with NX_ENV_ABS, param_a tracking
saturation events (so caller knows whether the filter has reached
information-loss territory).
dependencies 3 imports · 0 importers
imports: nx_syscalls.nxnx_murmur3.nxnx_sketch_types.nx
imported by: nobody (leaf or entry point)
structs
| 41 | struct CountingBloom |
consts
| 38 | const NX_CB_COUNTER_MAX: i64 = 15 // 4-bit counters; saturates at 15 |
| 39 | const NX_CB_COUNTERS_PER_BYTE: i64 = 2 // 4-bit packed two per byte |
functions
| 52 | func nx_cb_counter_get(cb: *CountingBloom, idx: i64) -> i64 |
| 60 | func nx_cb_counter_set(cb: *CountingBloom, idx: i64, value: i64) -> i64 |
| 76 | func nx_cb_is_pow2(n: i64) -> i64 called by 1: nx_cb_alloc |
| 82 | func nx_cb_alloc(cap_counters: i64, k: i64) -> *CountingBloom |
| 112 | func nx_cb_insert(cb: *CountingBloom, key: *u8, len: i64) -> i64 |
| 132 | func nx_cb_contains(cb: *CountingBloom, key: *u8, len: i64) -> i64 |
| 145 | func nx_cb_delete(cb: *CountingBloom, key: *u8, len: i64) -> i64 |
| 180 | func nx_cb_estimate_multiplicity(cb: *CountingBloom, key: *u8, len: i64) -> i64 |
| 198 | func nx_cb_fpr_ppb(cb: *CountingBloom) -> i64 called by 1: nx_cb_query |
| 211 | func nx_cb_query(cb: *CountingBloom, key: *u8, len: i64) -> *ApproxI64 |
| 225 | func nx_cb_merge(a: *CountingBloom, b: *CountingBloom) -> *CountingBloom |
| 247 | func nx_cb_saturations(cb: *CountingBloom) -> i64 |
| 251 | func nx_cb_memory_bytes(cb: *CountingBloom) -> i64 |