From bfa590269c8bd8d55d475d3842ff2207ad11f953 Mon Sep 17 00:00:00 2001 From: spark Date: Mon, 26 Oct 2026 11:18:04 +0000 Subject: [PATCH] beam: Q76 -- median cells are collected by the lane gate, and CHECK is green unmasked test_sliding_window_median.py: the seven cells were module-level functions behind `if __name__ == "__main__"`, so `unittest discover` collected none of them -- `python3 -m unittest test_sliding_window_median` printed `Ran 0 tests` (rc 5 on Python 3.14) and the lane gate stayed at `Ran 151` while a module with a floored even-median passed it at rc 0. They are TestCase methods now, with the same seven assertions, the module resolved from this file's directory (Q61 rule), and one added cell, test_cell_census, which pins the count at 8 so a deleted cell is a red gate. test_robin_hood_hash.py: `sys.path.insert(0, "/root/.hermes/wizard-outputs /beam")` -> `str(pathlib.Path(__file__).resolve().parent)`. That host insert is what made CHECK rc 1 unmasked with `ImportError: 'test_safe_eval' module incorrectly imported from /root/.hermes/wizard-outputs/beam`. Measured at this commit: `bash wizard-work/beam/CHECK` rc 0, `Ran 159 tests`, OK -- unmasked, with /root/.hermes/wizard-outputs masked to an empty tmpfs, and in a copied lane with no .git. 151 + 8 = 159. Mutants: 8 of 9 killed (M8 is an equivalent mutant, 0 differences in 20,000 batch and 5,000 incremental cases); with the old test file and a floored even-median the gate is rc 0, Ran 151, OK. Record: wizard-work/volt/q76-2026-10-26.md. --- wizard-work/beam/test_robin_hood_hash.py | 12 +- .../beam/test_sliding_window_median.py | 120 ++++++++++++------ wizard-work/volt/q76-2026-10-26.md | 103 +++++++++++++++ 3 files changed, 194 insertions(+), 41 deletions(-) create mode 100644 wizard-work/volt/q76-2026-10-26.md diff --git a/wizard-work/beam/test_robin_hood_hash.py b/wizard-work/beam/test_robin_hood_hash.py index 1a43ad2..6bb4e4d 100644 --- a/wizard-work/beam/test_robin_hood_hash.py +++ b/wizard-work/beam/test_robin_hood_hash.py @@ -1,5 +1,13 @@ -import random, sys -sys.path.insert(0, "/root/.hermes/wizard-outputs/beam") +import pathlib, random, sys + +# Q76 / 2026-10-26: resolve robin_hood_hash from THIS file's directory and from +# nowhere else (Q61 / test_toposort.py rule). This line used to read +# sys.path.insert(0, "/root/.hermes/wizard-outputs/beam"), which put a HOST +# directory first on sys.path for the whole `unittest discover` process; that is +# what made this lane's CHECK rc 1 with +# ImportError: 'test_safe_eval' module incorrectly imported from +# '/root/.hermes/wizard-outputs/beam'. Expected '.../wizard-work/beam'. +sys.path.insert(0, str(pathlib.Path(__file__).resolve().parent)) from robin_hood_hash import RobinHoodHash for trial in range(300): diff --git a/wizard-work/beam/test_sliding_window_median.py b/wizard-work/beam/test_sliding_window_median.py index 5fa7ba1..61dbf22 100644 --- a/wizard-work/beam/test_sliding_window_median.py +++ b/wizard-work/beam/test_sliding_window_median.py @@ -1,50 +1,92 @@ -import random, statistics -from sliding_window_median import sliding_window_median, SlidingWindowMedian +"""Tests for sliding_window_median. + +Runs two ways, both against the bytes in this directory: + python3 -m unittest test_sliding_window_median -v + python3 -m unittest discover -p 'test_*.py' (this lane's CHECK) + +Q76 / 2026-10-26: the seven cells were module-level functions called from an +`if __name__ == "__main__"` loop, so `unittest` collected none of them -- +`python3 -m unittest test_sliding_window_median` printed `Ran 0 tests` and +returned rc 0 while 158 lines of module + tests sat outside the lane gate. +They are TestCase methods now, which is what `discover` collects. The module +under test is resolved from THIS file's directory and from nowhere else (the +Q61 / test_toposort.py rule): a host-directory `sys.path.insert` here is what +made this lane's CHECK red from 2026-10-25 08:02 onward. +""" +import pathlib +import random +import sys +import unittest + +HERE = pathlib.Path(__file__).resolve().parent +sys.path.insert(0, str(HERE)) + +from sliding_window_median import sliding_window_median, SlidingWindowMedian # noqa: E402 + def brute(nums, k): - out=[] - for i in range(len(nums)-k+1): - w=sorted(nums[i:i+k]) - if k%2: out.append(float(w[k//2])) - else: out.append((w[k//2-1]+w[k//2])/2.0) + out = [] + for i in range(len(nums) - k + 1): + w = sorted(nums[i:i + k]) + if k % 2: + out.append(float(w[k // 2])) + else: + out.append((w[k // 2 - 1] + w[k // 2]) / 2.0) return out -def test_basic(): - assert sliding_window_median([1,3,-1,-3,5,3,6,7],3)==[1.0, -1.0, -1.0, 3.0, 5.0, 6.0] -def test_even(): - assert sliding_window_median([1,2,3,4],2)==[1.5,2.5,3.5] +class TestSlidingWindowMedian(unittest.TestCase): + def test_basic(self): + self.assertEqual( + sliding_window_median([1, 3, -1, -3, 5, 3, 6, 7], 3), + [1.0, -1.0, -1.0, 3.0, 5.0, 6.0], + ) -def test_single(): - assert sliding_window_median([5],1)==[5.0] + def test_even(self): + self.assertEqual(sliding_window_median([1, 2, 3, 4], 2), [1.5, 2.5, 3.5]) -def test_empty(): - assert sliding_window_median([],3)==[] - assert sliding_window_median([1,2],0)==[] + def test_single(self): + self.assertEqual(sliding_window_median([5], 1), [5.0]) -def test_random(): - for _ in range(300): - n=random.randint(1,40) - k=random.randint(1,n) - nums=[random.randint(-20,20) for _ in range(n)] - got=sliding_window_median(nums,k) - exp=brute(nums,k) - assert len(got)==len(exp) - for a,b in zip(got,exp): - assert abs(a-b)<1e-9, (nums,k,a,b) + def test_empty(self): + self.assertEqual(sliding_window_median([], 3), []) + self.assertEqual(sliding_window_median([1, 2], 0), []) -def test_incremental(): - swm=SlidingWindowMedian(3) - assert swm.add(1) is None - assert swm.add(3) is None - assert swm.add(-1)==1.0 - assert swm.add(-3)==-1.0 + def test_random(self): + for _ in range(300): + n = random.randint(1, 40) + k = random.randint(1, n) + nums = [random.randint(-20, 20) for _ in range(n)] + got = sliding_window_median(nums, k) + exp = brute(nums, k) + self.assertEqual(len(got), len(exp)) + for a, b in zip(got, exp): + self.assertLess(abs(a - b), 1e-9, (nums, k, a, b)) -def test_duplicates_removal(): - # duplicates where removal ambiguity exists - assert sliding_window_median([2,2,2,2],2)==[2.0,2.0,2.0] + def test_incremental(self): + swm = SlidingWindowMedian(3) + self.assertIsNone(swm.add(1)) + self.assertIsNone(swm.add(3)) + self.assertEqual(swm.add(-1), 1.0) + self.assertEqual(swm.add(-3), -1.0) -if __name__=="__main__": - for name in [n for n in globals() if n.startswith("test_")]: - globals()[name]() - print("ALL PASS") + def test_duplicates_removal(self): + # duplicates where removal ambiguity exists + self.assertEqual(sliding_window_median([2, 2, 2, 2], 2), [2.0, 2.0, 2.0]) + + def test_cell_census(self): + """Pin how many cells this file has, so a deleted cell is a red gate. + + The Q76 fault was quantitative: 158 lines landed, 0 cells were + collected, and the lane's `Ran 151` did not move. A deletion cannot + redden a green suite on its own -- nothing fails when a passing cell + disappears -- so the count is asserted here, next to the cells it + counts. Adding a cell means bumping this number in the same commit, + exactly as a `Ran N tests` move is stated in the commit message. + """ + cells = sorted(n for n in dir(self) if n.startswith("test_")) + self.assertEqual(len(cells), 8, cells) # 7 behaviour cells + this census + + +if __name__ == "__main__": + unittest.main() diff --git a/wizard-work/volt/q76-2026-10-26.md b/wizard-work/volt/q76-2026-10-26.md new file mode 100644 index 0000000..0608199 --- /dev/null +++ b/wizard-work/volt/q76-2026-10-26.md @@ -0,0 +1,103 @@ +# Q76 — beam's seven median cells are collected by the lane gate now, and the lane CHECK is green unmasked + +**Q76 — CLOSED (2026-10-26, volt) at the commit that lands this record: the seven `test_sliding_window_median` cells are `unittest.TestCase` methods so `discover` collects them — the lane's `Ran 151 tests` becomes `Ran 159` — `test_robin_hood_hash.py` resolves its module from its own directory instead of `/root/.hermes/wizard-outputs/beam`, and `bash wizard-work/beam/CHECK` is **rc 0 unmasked**, in a copied tree with no `.git`, and red on a sabotaged module and on a deleted cell.** + +Tier: **Documented** — my own copies, my own mutants, my own runs; every rc below comes from a `subprocess` return code, never from a pipeline's tail. + +## 1. The fault, both clauses, re-measured at `cd972a9` + +**(a) Collection.** `wizard-work/beam/test_sliding_window_median.py` was 50 lines: seven module-level functions called from an `if __name__ == "__main__"` loop. Measured on a copy of the committed blob: + +- `python3 -m unittest test_sliding_window_median` → **`Ran 0 tests`, `NO TESTS RAN`, rc 5**. Under Python 3.14.7 a discovery invocation that collects nothing exits **5**; the opening record's `rc 0` for this command is a pipeline artifact, not the interpreter's code — the collection finding is unchanged and the number is corrected here. +- `python3 test_sliding_window_median.py` → `ALL PASS`, rc 0 (the cells do run when the file is executed as a script). +- **The gate.** In a copy of the whole lane with the module sabotaged — `return (-self.lo[0] + self.hi[0]) / 2.0` → `return float(-self.lo[0])` (even median floored) — and the test file exactly as committed: `bash CHECK` → **rc 0, `Ran 151 tests`, `OK`, `ALL PASS`**. A module that returns the wrong median for every even window passes the lane gate. That is the fault, and it is quantitative: 108 + 50 = **158** lines landed and the count did not move. + +**(b) The host path.** `test_robin_hood_hash.py:2` was `sys.path.insert(0, "/root/.hermes/wizard-outputs/beam")`, executed at import by `unittest discover`, so the **host** directory sat ahead of the lane on `sys.path` for every module discovery imported afterwards: + +- unmasked `bash CHECK` at `cd972a9` → **rc 1**, `ImportError: 'test_safe_eval' module incorrectly imported from '/root/.hermes/wizard-outputs/beam'. Expected '/root/troupe-standup/wizard-work/beam'`, `Ran 0 tests`; +- masked (`unshare -m` + tmpfs over `/root/.hermes/wizard-outputs`, 0 entries) → **rc 0, `Ran 151 tests`, `OK`**. + +The host directory holds 38 `test_*.py` files, `test_safe_eval.py` among them since 2026-10-23 17:15. A real break in this lane would have been indistinguishable from this red — Q62's class, inside the gate that grades the lane. + +## 2. The fix + +`wizard-work/beam/test_sliding_window_median.py` (50 → 92 lines, `sha256 9ab3dbe304434703…`): + +- the seven cells are `class TestSlidingWindowMedian(unittest.TestCase)` methods with the **same seven assertions** (`assertX` → `self.assertEqual`, each argument preserved: the LeetCode vector, the even window, the single window, empty/k≤0, the 300-trial `brute()` differential, the 4-step incremental trace, and the `[2,2,2,2]` duplicate-removal case); no cell was dropped, weakened or merged; +- `brute()` is kept as the independent oracle; +- the module under test is resolved from `pathlib.Path(__file__).resolve().parent` and nowhere else (the Q61 / `test_toposort.py` rule), stated in the docstring; +- one cell was **added**, `test_cell_census` (§5), because a deleted cell cannot redden a green suite on its own — the count is asserted next to the cells it counts; +- `__main__` is `unittest.main()`, so both invocations run the same eight cells. + +`wizard-work/beam/test_robin_hood_hash.py` (28 → 36 lines, `sha256 a22bd8efbbe20d19…`): the host `sys.path.insert` is replaced by `str(pathlib.Path(__file__).resolve().parent)`, with the old line quoted in the comment. Nothing else in that file changed — its 300 module-body trials are its oracle and they still run at import, which is what makes a failure surface as a discovery error rather than a silent pass. + +Measured, three ways: + +| run | rc | result | +|---|---|---| +| `python3 -m unittest test_sliding_window_median` | 0 | `Ran 8 tests`, `OK` | +| `python3 test_sliding_window_median.py` | 0 | `Ran 8 tests`, `OK` | +| `bash wizard-work/beam/CHECK`, **unmasked**, worktree | **0** | **`Ran 159 tests`**, `OK` | +| `bash CHECK`, masked (`/root/.hermes/wizard-outputs` = empty tmpfs) | 0 | `Ran 159 tests`, `OK` | +| `bash CHECK`, whole lane copied to scratch, **no `.git`** | 0 | `Ran 159 tests`, `OK` | + +`151 + 8 = 159`: the lane's count moves by exactly the cells this file now contributes. + +## 3. The mutant battery — what the cells are worth + +Nine mutants of `sliding_window_median.py`, each a one-substitution copy, graded by `python3 -m unittest discover -p 'test_*.py'` in a four-file tree: + +| mutant | rc | failing cells | +|---|---|---| +| M1 even median floored | 1 | `test_even`, `test_random` | +| M2 `remove()` no-op | 1 | `test_basic`, `test_even`, `test_incremental`, `test_random` | +| M3 `_balance()` no-op | 1 | `test_basic`, `test_even`, `test_random` (+2 errors) | +| M4 odd median from `hi[0]` | 1 | `test_basic`, `test_incremental`, `test_random` | +| M5 buffer pops the wrong end | 1 | `test_basic`, `test_even`, `test_incremental`, `test_random` | +| M6 `_prune()` no-op | 1 | `test_basic`, `test_random` | +| M7 window off-by-one (`> k+1`) | 1 | five cells | +| M8 insert routing `<=` → `<` | **0** | none — **equivalent mutant**, see below | +| M9 `remove()` routing `<=` → `<` | 1 | `test_basic`, `test_duplicates_removal`, `test_random` | + +**8 of 9 killed.** M8 is not a gap: routing a value equal to the current boundary into `hi` instead of `lo` is invisible because `_balance()` restores the invariant and lazy deletion is keyed by value, not by side. Measured against the wildtype at the value level: **0 differences in 20,000 batch cases** (n ≤ 30, k ≤ 8, values in [-4,4]) and **0 in 5,000 incremental op-by-op sequences** — an equivalent mutant, recorded as a null. + +The same nine mutants against the **old** file, invoked the other way it could have been invoked — `python3 test_sliding_window_median.py`, its own `__main__` loop: 8 of 9 red (M8 green, same null). So the cells were always real; what was missing was a caller. `discover` was not calling them, and that is the whole finding. + +## 4. Negative cells + +| cell | tree | command | rc | what it proves | +|---|---|---|---|---| +| A | full lane, **old** test file + M1 | `bash CHECK` | **0** (`Ran 151`, `OK`) | the fault: a wrong even-median passes the gate | +| B | four-file tree, new file + M1 | `discover -p 'test_*.py'` | 1 | the fix: `Ran 8`, `FAILED (failures=2)`, `[1.0, 2.0, 3.0] != [1.5, 2.5, 3.5]` | +| C | four-file tree, new file, wildtype | `discover -p 'test_*.py'` | 0 | no false red | +| D | four-file tree, new file **minus `test_duplicates_removal`** | `discover -p 'test_*.py'` | **1** | a deleted cell is red: `AssertionError: 7 != 8` naming the seven survivors | +| E | four-file tree, minus duplicates and random | `discover -p 'test_*.py'` | 1 | two deletions: `6 != 8` | +| F | four-file tree, minus `test_cell_census` | `discover -p 'test_*.py'` | **0** | the census's own blind spot, measured in §5 | +| G | whole lane copy, M3 sabotage | `bash CHECK` | **1** | `Ran 159 tests`, `FAILED (errors=3)` | +| H | whole lane copy, wildtype | `bash CHECK` | 0 | `Ran 159 tests`, `OK`, no `.git`, no host state | + +## 5. The census cell, and its limit + +`test_cell_census` asserts `len([n for n in dir(self) if n.startswith("test_")]) == 8` — the seven behaviour cells plus itself. It exists because Q76's fault was quantitative: a deletion of a passing cell fails nothing, so "a cell deleted turns the gate red" needs a count. Cell D is that negative cell (`7 != 8`, the survivors printed). Its limit is measured and recorded rather than hidden: deleting the census cell itself returns **rc 0, `Ran 7 tests`, `OK`** (cell F) — a cell that counts cannot verify its own presence, and the lane's `Ran N` line is the second instrument for exactly that case. Adding a cell means bumping the number in the same commit, which is the same discipline as stating `Ran N` in a commit message. + +## 6. What is not claimed + +- **No complexity claim** is made or broken here; the module's O(nk) `buf.pop(0)` behaviour is untouched and the opening record already recorded it as a null. +- **`remove()`'s routing by the current boundary** rather than by insertion side looked wrong on paper and survived 11,763 brute-force trials before this change and 8 of the nine mutants here; it is unbroken, not proven. +- **M8's equivalence is measured on these distributions**, not proved: 25,000 cases, no difference. A distribution-dependent difference is not excluded. +- **Nothing about the other lanes.** Two files in beam's lane were edited — the two the item names — and no other file in `wizard-work/beam/` was touched (`git diff --stat` = these two files only). `toposort/` and the other 38 test modules are unchanged and still run under the same `CHECK`. +- **The count is an instrument, not a promise.** `Ran 159` is what this tree produced in these three environments; it is not a claim about any other checkout. + +## 7. Reproduce + +``` +cd wizard-work/beam +bash CHECK # rc 0, Ran 159 tests, OK (unmasked) +unshare -m bash -c 'mount -t tmpfs none /root/.hermes/wizard-outputs && bash CHECK' # rc 0, Ran 159 +python3 -m unittest test_sliding_window_median -v # Ran 8 tests, OK +``` + +Harnesses and transcripts, `/root/.hermes/profiles/volt/cache/scratch/q76/`: +`battery.py` (9 mutants × old/new, `battery.txt`), `detail.py` (per-mutant cells, old-file invocations, M8 differential, `detail.txt`), `gate.py` (cells A–H, `gate.txt`), `cell_i.py` (cell A, appended to `gate.txt`), `rc_probe.py` (`rc_probe.txt`), trees under `trees/`, `full_lane/`, `full_oldm1/`. + +Nothing from `inbox/` is quoted. Read, not edited: every other lane's files.