c214abcfa88b8eeecda41555e69d295c7010758c
2 Commits
| Author | SHA1 | Message | Date | |
|---|---|---|---|---|
|
|
e2ca2fc7d8 |
fix(guns): recover the DrussGT regression with a radial-fraction range blend
The previous fix (learn the residual against a constant-velocity base) was structurally right but cost us on real wave-surfing movement: GF 108 -> 55, KNN 101 -> 74 on the classic DrussGT captures. Root cause: the linear base is a poor model for a surfer, so the residual histogram is noisier than the old total-lead histogram. FIX: blend the RANGE between a radial-only forecast and the geometric one by radialFrac (the fraction of recent per-tick motion that is radial), keeping the constant-velocity bearing. dist = radialDist + rf*(linearDist - radialDist). New VelocityTracker in common_libs/guns/lead_forecast.nim; the window default is 32 and results were identical at 16 and 40, so it is not tightly tuned. Nine candidate bases were measured and rejected WITH NUMBERS rather than by argument, which is why I trust the winner: velocity scaling 0.8 recovers DrussGT but destroys wall-bounce 241 -> 20 radial-only range excellent DrussGT, wall-bounce 241 -> 140 short-window averaged vel worse than both bases outright hard reversal/speed gates help DrussGT, lose nothing, but weaker than blend radial-fraction blend best on BOTH <- shipped Result (hits per 2000; classic-5 = classic DrussGT captures, tr-5 = the new closed-loop TR captures, synth-10 = the rest): base classic-5 GF/DGF tr-5 GF/DGF synth-10 GF/DGF current(prefix) 108 / 108 41 / 39 1302 / 1302 linear(postfix) 55 / 76 9 / 4 2702 / 2692 BLEND 171 / 100 86 / 87 2717 / 2703 Strictly better than both on classic-5 GF and on every synthetic bucket. The one figure below the old base is classic-5 DecayGF (108 -> 100, -8/2000, within noise) and that is stated plainly rather than hidden. TASK B - enemy energy in learners. KNN gains an 8th feature, enemyEnergy/100, on a FIXED [0,1] scale (not min-max) because threshold behaviour keys off absolute energy. Honest result: it is NEUTRAL on the target fixture (77 vs 77) and roughly neutral in aggregate. The base change, not the feature, moved that fixture. Tsetlin already encoded enemyEnergy and now scores 88/400 on energy-threshold-turner against Linear's 43/400 - a 2x margin, which is the 'can a TM learn a high-level pattern' question answered in gun form. TASK C - is the virtual-bullet metric itself faithful? Quantified: scoring the bullet's PATH against BotRadius instead of the single point at aim distance raises every gun by +31% (GF) to +86% (HeadOn), so the current model is PESSIMISTIC, and it RE-RANKS materially: Linear 9th -> 6th, AvgLead 7th -> 3rd, GuessFactor 4th -> 9th, DecayGF 6th -> 12th. The 12/12 offline==online acceptance still holds under the path model (verified with a temporary env hook driving both sides), so no red flag. VERDICT: do NOT switch. The point model is the standard virtual-bullet PREDICTION-ACCURACY fitness - the bullet must arrive at the predicted point at the right time - while the path model measures hypothetical hit chance against a target that never dodges, and in open-loop fixtures it over-credits directional guns (HeadOn 35% on DrussGT, 100% on constant-velocity) for exactly that reason. The models differ materially but the current one is not shown to be unfaithful FOR ITS PURPOSE. Because the metric drives gun SELECTION, this is now being A/B'd against real hit rate versus the live DrussGT boss, which is the only ground truth we have. Verified: 20 fixtures 35636/104000 (34.3%); 33 guard checks; 12/12 acceptance; tsetlin tests green; live gauntlet 5/5. |
||
|
|
7f706e5b14 |
fix(guns): GF family aimed at the wrong RADIUS, not the wrong angle
The entire GuessFactor family scored 0% on clean circular and wall-bounce trajectories. Two hypotheses were on the table and BOTH were wrong: - MEA range too narrow / edge clamping: REFUTED. Measured 0 clamped shots out of 837/849/957, required offsets peak at ~33 deg against MEA 28.1-46.7 deg, and the 8 in arcsin(8/bulletSpeed) is correct (it is the max robot SPEED, not the hit radius). Changing it to BotRadius=18 would have coarsened resolution for nothing. - Peak selection: REFUTED. A sweep of every constant GF value showed the ORACLE-BEST constant offset on the original gun was only 6% circular, 4% wall-bounce, 7.5% random-walk. No peak choice could have done better. The learning path was fine too: ~850-960 observations per fixture, 0 starved waves, well-populated histograms. REAL CAUSE: the GF family aimed at the FIRE-TIME distance. The virtual-bullet metric resolves a bullet at the AIM-POINT distance and scores that single point against the enemy's position on that tick, so with any radial target motion the bullet stops at the wrong radius and misses even with a perfect angle. Angle-only prediction is structurally unscoreable under this metric. FIX: give the GF family a self-consistent constant-velocity forecast as its base reference (new common_libs/guns/lead_forecast.nim, which iterates the flight time to the same fixed point circular.nim uses), so the histogram learns the RESIDUAL against that forecast and the aim point lands at the right radius. Applied to guess_factor, decay_gf and knn_gun. Same defect fixed in Linear: it did a one-shot dist/bulletSpeed extrapolation and never iterated its flight time. The oracle sweep proves the structural fix, independently of tuning: the best achievable constant GF moved 6% -> 20% (circular), 4% -> 57% (wall-bounce), 7.5% -> 49% (random-walk). MEASURED, all 15 fixtures: total 39.0% -> 44.4% (30399 -> 34654 hits). circular GF 6 -> 23, DecayGF 6 -> 21 wall-bounce GF 0 -> 60.2, DecayGF 0 -> 60.2 constant-vel GF 26 -> 100, DecayGF 26 -> 100, KNN 26 -> 100, Linear 87 -> 100 random-walk GF 0 -> 53, DecayGF 0 -> 52, Linear 24 -> 53 StraightLine GF 8 -> 77, DecayGF 8 -> 77 Non-regression: 33 guard checks pass, the range's 12/12 offline==online acceptance still PASSES, tsetlin tests green, live gauntlet 5/5. HONEST TRADE-OFF, recorded rather than hidden: on the 5 real DrussGT wave-surfing captures the GF family REGRESSES - GuessFactor 108 -> 55, DecayGF 108 -> 76, KNN 101 -> 74 hits per 2000. The linear base is a poor model for a surfer, so the residual histogram is noisier than the old total-lead histogram. Linear itself improved there (95 -> 105). The synthetic range and the live gauntlet both improved, and the structural bug is provably fixed, so this was judged worth the cost - but recovering the DrussGT regression is the next job, not something to wave away. |