code wiki / (root) / sketch_cpc_dense_test.nx

sketch_cpc_dense_test.nx source

↩ module page · 137 lines · 3981 B

1// sketch_cpc_dense_test.nx -- CPC dense-mode verification. 2 3import "syscalls.nx" 4import "sketch_cpc_dense.nx" 5import "sketch_types.nx" 6 7func iabs(x: i64) -> i64 { 8 if x < 0 { return -x } 9 return x 10} 11 12func main() -> i64 { 13 // ---- alloc ---- 14 // lg_k=5 (m=32), w=32 -> big_M = 1024. Bitmap = 128 bytes. 15 let c: *CpcDense = nx_cpcd_alloc(5, 32, 42) 16 if c == (0 as *CpcDense) { return __syscall(93, 5, 0, 0, 0, 0, 0) } 17 if nx_cpcd_alloc(1, 32, 1) != (0 as *CpcDense) { 18 return __syscall(93, 6, 0, 0, 0, 0, 0) 19 } 20 if nx_cpcd_alloc(5, 100, 1) != (0 as *CpcDense) { 21 return __syscall(93, 7, 0, 0, 0, 0, 0) 22 } 23 if nx_cpcd_big_m(c) != 1024 { 24 return __syscall(93, 8, 0, 0, 0, 0, 0) 25 } 26 // 128 bytes bitmap + 72 header = 200 bytes total. 27 if nx_cpcd_memory_bytes(c) != 200 { 28 return __syscall(93, 9, 0, 0, 0, 0, 0) 29 } 30 31 // ---- empty: estimate = 0 ---- 32 if nx_cpcd_estimate(c) != 0 { 33 return __syscall(93, 10, 0, 0, 0, 0, 0) 34 } 35 36 // ---- single insertion: HIP estimate = 1 ---- 37 nx_cpcd_add(c, "alice", 5) 38 if nx_cpcd_estimate(c) != 1 { 39 return __syscall(93, 20, 0, 0, 0, 0, 0) 40 } 41 if nx_cpcd_n_set(c) != 1 { 42 return __syscall(93, 21, 0, 0, 0, 0, 0) 43 } 44 45 // ---- 100 distinct: estimate ~ 100 ---- 46 let c2: *CpcDense = nx_cpcd_alloc(5, 32, 7) 47 let buf: *u8 = sys_mmap(8) 48 var i: i64 = 0 49 while i < 100 { 50 buf[0] = (i ) & 0xFF 51 buf[1] = (i >> 8 ) & 0xFF 52 buf[2] = 0x30 53 buf[3] = 0 54 buf[4] = 0 55 buf[5] = 0 56 buf[6] = 0 57 buf[7] = 0 58 nx_cpcd_add(c2, buf, 8) 59 i = i + 1 60 } 61 let e100: i64 = nx_cpcd_estimate(c2) 62 // big_M=1024 -> stddev ~3.1%. Allow +/-15. 63 if iabs(e100 - 100) > 15 { 64 return __syscall(93, 30, 0, 0, 0, 0, 0) 65 } 66 67 // ---- idempotent inserts ---- 68 let c3: *CpcDense = nx_cpcd_alloc(5, 32, 1) 69 nx_cpcd_add(c3, "x", 1) 70 nx_cpcd_add(c3, "x", 1) 71 nx_cpcd_add(c3, "x", 1) 72 if nx_cpcd_n_set(c3) != 1 { 73 return __syscall(93, 40, 0, 0, 0, 0, 0) 74 } 75 if nx_cpcd_estimate(c3) != 1 { 76 return __syscall(93, 41, 0, 0, 0, 0, 0) 77 } 78 79 // ---- typed envelope ---- 80 let q: *ApproxI64 = nx_cpcd_query(c2) 81 if q.envelope_kind != NX_ENV_REL_STDDEV { 82 return __syscall(93, 50, 0, 0, 0, 0, 0) 83 } 84 // big_M=1024 -> isqrt(1024)=32 -> stddev_ppb = 1e9/32 = 31_250_000. 85 if iabs(q.param_a - 31250000) > 1000 { 86 return __syscall(93, 51, 0, 0, 0, 0, 0) 87 } 88 if q.maturity != NX_MATURITY_PRODUCTION { 89 return __syscall(93, 52, 0, 0, 0, 0, 0) 90 } 91 92 // ---- merge ---- 93 let m_a: *CpcDense = nx_cpcd_alloc(5, 32, 99) 94 let m_b: *CpcDense = nx_cpcd_alloc(5, 32, 99) 95 i = 0 96 while i < 50 { 97 buf[0] = (i ) & 0xFF 98 buf[1] = (i >> 8 ) & 0xFF 99 buf[2] = 0x80 100 buf[3] = 0 101 buf[4] = 0 102 buf[5] = 0 103 buf[6] = 0 104 buf[7] = 0 105 nx_cpcd_add(m_a, buf, 8) 106 i = i + 1 107 } 108 i = 50 109 while i < 100 { 110 buf[0] = (i ) & 0xFF 111 buf[1] = (i >> 8 ) & 0xFF 112 buf[2] = 0x80 113 buf[3] = 0 114 buf[4] = 0 115 buf[5] = 0 116 buf[6] = 0 117 buf[7] = 0 118 nx_cpcd_add(m_b, buf, 8) 119 i = i + 1 120 } 121 let merged: *CpcDense = nx_cpcd_merge(m_a, m_b) 122 if merged == (0 as *CpcDense) { 123 return __syscall(93, 60, 0, 0, 0, 0, 0) 124 } 125 let e_merged: i64 = nx_cpcd_estimate(merged) 126 // True cardinality of union = 100. Allow +/-15. 127 if iabs(e_merged - 100) > 15 { 128 return __syscall(93, 61, 0, 0, 0, 0, 0) 129 } 130 // Mismatched seed -> NULL. 131 let m_c: *CpcDense = nx_cpcd_alloc(5, 32, 88) 132 if nx_cpcd_merge(m_a, m_c) != (0 as *CpcDense) { 133 return __syscall(93, 62, 0, 0, 0, 0, 0) 134 } 135 136 return 0 137}