code wiki / _hdl_build / nx_dataframe_gate.nx
nx_dataframe_gate.nx source
↩ module page · 136 lines · 6626 B
1import "nx_gate_gn.nx"
2// nx_dataframe_gate.nx -- GATE for the aggregation front door (nx_dataframe). Known-answer tests on a fixed
3// column so every reduction, predicate scan, quantile, GROUP BY, and inner join is proven EXACT (integer-
4// reproducible). Anti-false-green: a deliberately-wrong expected value is NOT used; every assert is the true
5// hand-computed answer. expect_exit: 0 license_tier: ORIGINAL
6import "nx_syscalls.nx"
7import "_hdl_build/nx_dataframe.nx"
8
9func gp(s: *u8) -> i64 { var n: i64=0; while s[n]!=(0 as u8){n=n+1} sys_write(1,s,n); return 0 }
10
11func main() -> i64 {
12 gp("=== nx_dataframe_gate ===\n" as *u8)
13 var pass: i64 = 0
14 var fail: i64 = 0
15
16 // column = [5, 2, 9, 2, 7, 5] (n=6) sum=30 min=2 max=9 mean=5 (30/6) sorted=[2,2,5,5,7,9]
17 let col: *i64 = sys_mmap(6 * 8) as *i64
18 col[0]=5; col[1]=2; col[2]=9; col[3]=2; col[4]=7; col[5]=5
19 let n: i64 = 6
20
21 // T1 reductions
22 var t1: i64 = 1
23 if df_count(col, n) != 6 { t1 = 0 }
24 if df_sum(col, n) != 30 { t1 = 0 }
25 if df_min(col, n) != 2 { t1 = 0 }
26 if df_max(col, n) != 9 { t1 = 0 }
27 if t1 == 1 { pass = pass + 1 } else { fail = fail + 1; gp("T1 FAIL reductions\n" as *u8) }
28
29 // T2 mean + remainder + milli mean (30/6 = 5 exact; milli = 5000)
30 var t2: i64 = 1
31 let rem: *i64 = sys_mmap(8) as *i64
32 if df_mean(col, n, rem) != 5 { t2 = 0 }
33 if rem[0] != 0 { t2 = 0 }
34 if df_mean_milli(col, n) != 5000 { t2 = 0 }
35 if t2 == 1 { pass = pass + 1 } else { fail = fail + 1; gp("T2 FAIL mean\n" as *u8) }
36
37 // T3 mean with remainder on a non-divisible column [1,2,3,4] sum=10 n=4 mean=2 rem=2 milli=2500
38 let c2: *i64 = sys_mmap(4 * 8) as *i64
39 c2[0]=1; c2[1]=2; c2[2]=3; c2[3]=4
40 var t3: i64 = 1
41 if df_mean(c2, 4, rem) != 2 { t3 = 0 }
42 if rem[0] != 2 { t3 = 0 }
43 if df_mean_milli(c2, 4) != 2500 { t3 = 0 }
44 if t3 == 1 { pass = pass + 1 } else { fail = fail + 1; gp("T3 FAIL mean-remainder\n" as *u8) }
45
46 // T4 variance + stddev on [2,4,4,4,5,5,7,9]: mean=5, var=4, stddev=2 (textbook)
47 let c3: *i64 = sys_mmap(8 * 8) as *i64
48 c3[0]=2; c3[1]=4; c3[2]=4; c3[3]=4; c3[4]=5; c3[5]=5; c3[6]=7; c3[7]=9
49 var t4: i64 = 1
50 let vm: i64 = df_var_milli(c3, 8) // 4 * 1000 = 4000
51 if vm != 4000 { t4 = 0 }
52 if df_isqrt(vm / 1000) != 2 { t4 = 0 } // sqrt(4) = 2
53 if df_isqrt(9) != 3 { t4 = 0 }
54 if df_isqrt(10) != 3 { t4 = 0 } // floor
55 if t4 == 1 { pass = pass + 1 } else { fail = fail + 1; gp("T4 FAIL variance/stddev\n" as *u8) }
56
57 // T5 predicate scans on col [5,2,9,2,7,5]: >=5 -> {5,9,7,5}=4 count, sum=26 ; ==2 -> 2 count
58 var t5: i64 = 1
59 if df_filter_count(col, n, 4, 5) != 4 { t5 = 0 } // >=5
60 if df_filter_sum(col, n, 4, 5) != 26 { t5 = 0 }
61 if df_filter_count(col, n, 0, 2) != 2 { t5 = 0 } // ==2
62 if df_filter_count(col, n, 1, 5) != 2 { t5 = 0 } // <5 -> {2,2}
63 if t5 == 1 { pass = pass + 1 } else { fail = fail + 1; gp("T5 FAIL predicate scan\n" as *u8) }
64
65 // T6 quantiles on sorted [2,2,5,5,7,9]: min(q0)=2, max(q1000)=9, median(q500)=rank (500*5/1000)=2 -> cp[2]=5
66 var t6: i64 = 1
67 if df_quantile(col, n, 0) != 2 { t6 = 0 }
68 if df_quantile(col, n, 1000) != 9 { t6 = 0 }
69 if df_quantile(col, n, 500) != 5 { t6 = 0 }
70 // the source column must be UNCHANGED (quantile sorts a copy)
71 if col[0] != 5 { t6 = 0 }
72 if col[1] != 2 { t6 = 0 }
73 if t6 == 1 { pass = pass + 1 } else { fail = fail + 1; gp("T6 FAIL quantile / column-immutability\n" as *u8) }
74
75 // T7 GROUP BY: keys=[1,2,1,3,2,1] vals=[10,20,30,40,50,60]
76 // count: g1=3 g2=2 g3=1 ; sum: g1=100 g2=70 g3=40
77 let gk: *i64 = sys_mmap(6 * 8) as *i64
78 let gv: *i64 = sys_mmap(6 * 8) as *i64
79 gk[0]=1; gk[1]=2; gk[2]=1; gk[3]=3; gk[4]=2; gk[5]=1
80 gv[0]=10; gv[1]=20; gv[2]=30; gv[3]=40; gv[4]=50; gv[5]=60
81 let ok: *i64 = sys_mmap(16 * 8) as *i64
82 let oa: *i64 = sys_mmap(16 * 8) as *i64
83 var t7: i64 = 1
84 let gc: i64 = df_groupby(gk, gv, 6, 0, ok, oa, 16) // count
85 if gc != 3 { t7 = 0 }
86 // groups emitted in first-seen order: key1,key2,key3
87 if ok[0] != 1 { t7 = 0 } else { if oa[0] != 3 { t7 = 0 } }
88 if ok[1] != 2 { t7 = 0 } else { if oa[1] != 2 { t7 = 0 } }
89 if ok[2] != 3 { t7 = 0 } else { if oa[2] != 1 { t7 = 0 } }
90 let gc2: i64 = df_groupby(gk, gv, 6, 1, ok, oa, 16) // sum
91 if gc2 != 3 { t7 = 0 }
92 if oa[0] != 100 { t7 = 0 }
93 if oa[1] != 70 { t7 = 0 }
94 if oa[2] != 40 { t7 = 0 }
95 if t7 == 1 { pass = pass + 1 } else { fail = fail + 1; gp("T7 FAIL groupby\n" as *u8) }
96
97 // T8 INNER JOIN: left keys=[1,2,3] vals=[100,200,300]; right keys=[2,3,4] vals=[22,33,44]
98 // matches: (200,22),(300,33) -> 2 rows
99 let lk: *i64 = sys_mmap(3 * 8) as *i64
100 let lv: *i64 = sys_mmap(3 * 8) as *i64
101 let rk: *i64 = sys_mmap(3 * 8) as *i64
102 let rv: *i64 = sys_mmap(3 * 8) as *i64
103 lk[0]=1; lk[1]=2; lk[2]=3; lv[0]=100; lv[1]=200; lv[2]=300
104 rk[0]=2; rk[1]=3; rk[2]=4; rv[0]=22; rv[1]=33; rv[2]=44
105 let jl: *i64 = sys_mmap(8 * 8) as *i64
106 let jr: *i64 = sys_mmap(8 * 8) as *i64
107 var t8: i64 = 1
108 let jn: i64 = df_inner_join(lk, lv, 3, rk, rv, 3, jl, jr, 8)
109 if jn != 2 { t8 = 0 }
110 if jl[0] != 200 { t8 = 0 } else { if jr[0] != 22 { t8 = 0 } }
111 if jl[1] != 300 { t8 = 0 } else { if jr[1] != 33 { t8 = 0 } }
112 if t8 == 1 { pass = pass + 1 } else { fail = fail + 1; gp("T8 FAIL inner join\n" as *u8) }
113
114 // T9 empty-column safety (no crash, sane zeros)
115 var t9: i64 = 1
116 let ec: *i64 = sys_mmap(8) as *i64
117 if df_count(ec, 0) != 0 { t9 = 0 }
118 if df_sum(ec, 0) != 0 { t9 = 0 }
119 if df_mean(ec, 0, rem) != 0 { t9 = 0 }
120 if df_quantile(ec, 0, 500) != 0 { t9 = 0 }
121 if t9 == 1 { pass = pass + 1 } else { fail = fail + 1; gp("T9 FAIL empty safety\n" as *u8) }
122
123 gp("pass=" as *u8); gn(pass); gp(" fail=" as *u8); gn(fail); gp("\n" as *u8)
124 let log: *u8 = sys_mmap(128)
125 var lo: i64 = 0
126 let pre: *u8 = "DATAFRAME authored=organ verdict=" as *u8
127 var pi: i64 = 0; while pre[pi]!=(0 as u8){log[lo]=pre[pi];lo=lo+1;pi=pi+1}
128 if fail == 0 { let g: *u8="GREEN\n" as *u8; var gi:i64=0; while g[gi]!=(0 as u8){log[lo]=g[gi];lo=lo+1;gi=gi+1} } else { let rr: *u8="RED\n" as *u8; var ri:i64=0; while rr[ri]!=(0 as u8){log[lo]=rr[ri];lo=lo+1;ri=ri+1} }
129 let fd: i64 = sys_openat_wr("knowledge/status/dataframe.log" as *u8, 0x1A4)
130 if fd >= 0 { sys_write(fd, log, lo); sys_close(fd) }
131
132 if fail == 0 { gp("=== DATAFRAME-GATE verdict=GREEN ===\n" as *u8); sys_exit(0); return 0 }
133 gp("=== DATAFRAME-GATE verdict=RED ===\n" as *u8)
134 sys_exit(1)
135 return 1
136}