From 5e4fc2bcb11a8a7e3d4aaedb4dd63f15cbdb8b4a Mon Sep 17 00:00:00 2001 From: jgrusewski Date: Fri, 27 Mar 2026 11:57:59 +0100 Subject: [PATCH] fix: integration tests for 22D search space + cql_alpha default mismatch - Update 3 integration tests in dqn_action_collapse_fix_test.rs that expected the old 46D search space (cql_alpha tunable, phase-specific v_range bounds). Now expect 22D with fixed cql_alpha. - Fix cql_alpha: from_continuous hardcoded 0.5, Default uses 0.1. Aligned to 0.1 (same pattern as dd_threshold fix earlier). Co-Authored-By: Claude Opus 4.6 (1M context) --- crates/ml/src/hyperopt/adapters/dqn.rs | 2 +- .../ml/tests/dqn_action_collapse_fix_test.rs | 56 ++++++++----------- 2 files changed, 25 insertions(+), 33 deletions(-) diff --git a/crates/ml/src/hyperopt/adapters/dqn.rs b/crates/ml/src/hyperopt/adapters/dqn.rs index 995e4ab74..cd2d7379e 100644 --- a/crates/ml/src/hyperopt/adapters/dqn.rs +++ b/crates/ml/src/hyperopt/adapters/dqn.rs @@ -663,7 +663,7 @@ impl ParameterSpace for DQNParams { activation_type: 1.0, noisy_epsilon_floor: 0.1, count_bonus_coefficient: 0.2, - cql_alpha: 0.5, + cql_alpha: 0.1, // match Default::default() eval_softmax_temp: 1.0, dsr_eta: 0.004, branch_hidden_dim: 64, diff --git a/crates/ml/tests/dqn_action_collapse_fix_test.rs b/crates/ml/tests/dqn_action_collapse_fix_test.rs index e350c56a1..ec6e45ce1 100644 --- a/crates/ml/tests/dqn_action_collapse_fix_test.rs +++ b/crates/ml/tests/dqn_action_collapse_fix_test.rs @@ -212,14 +212,14 @@ fn test_idle_penalty_in_gpu_composite_reward() { // ── 4. Hyperopt 26D search space includes cql_alpha ──────────────────────── #[test] -fn test_hyperopt_26d_includes_cql_alpha() { +fn test_hyperopt_22d_search_space() { use ml::hyperopt::adapters::dqn::DQNParams; use ml::hyperopt::traits::ParameterSpace; let bounds = DQNParams::continuous_bounds(); - assert!( - bounds.len() >= 39, - "Search space should be >= 39D, got {}D", + assert_eq!( + bounds.len(), 22, + "Search space should be 22D (consolidated from 46D), got {}D", bounds.len() ); @@ -231,36 +231,28 @@ fn test_hyperopt_26d_includes_cql_alpha() { names.len(), bounds.len() ); - // cql_alpha must exist in search space with bounds (0.0, 1.0) - let cql_idx = names.iter().position(|&n| n == "cql_alpha") - .expect("cql_alpha should be in param_names"); - let (lo, hi) = bounds[cql_idx]; + // cql_alpha is now FIXED at default (not in search space) assert!( - (lo - 0.0).abs() < 1e-6 && (hi - 1.0).abs() < 1e-6, - "cql_alpha bounds should be (0.0, 1.0), got ({}, {})", - lo, hi + !names.contains(&"cql_alpha"), + "cql_alpha should be fixed (not in 22D search space)" ); } #[test] -fn test_hyperopt_v_range_widened() { +fn test_hyperopt_v_max_in_search_space() { use ml::hyperopt::adapters::dqn::DQNParams; use ml::hyperopt::traits::ParameterSpace; let bounds = DQNParams::continuous_bounds(); + let names = DQNParams::param_names(); - // v_range at index 10: now computed dynamically from gamma. - // In Phase Fast, it's fixed to the TOML value (1.0 = placeholder, ignored). - // The actual v_range is computed in from_continuous() from gamma. - let (v_range_lo, v_range_hi) = bounds.get(10).copied().unwrap_or((0.0, 0.0)); - // Phase Fast fixes v_range to the TOML placeholder value - assert!( - (v_range_lo - v_range_hi).abs() < 1e-6, - "v_range should be fixed (single-point) in Phase Fast, got ({}, {})", - v_range_lo, v_range_hi - ); - - info!(v_range_lo, v_range_hi, "v_range bounds"); + // v_max is at index 14 in the 22D space with range [5, 300] + let v_max_idx = names.iter().position(|&n| n == "v_max") + .expect("v_max should be in param_names"); + let (lo, hi) = bounds[v_max_idx]; + assert!(lo >= 1.0 && hi <= 500.0, + "v_max bounds should be reasonable, got ({}, {})", lo, hi); + assert!(lo < hi, "v_max should have a range, got ({}, {})", lo, hi); } #[test] @@ -274,24 +266,24 @@ fn test_hyperopt_iqn_always_enabled() { } #[test] -fn test_hyperopt_cql_alpha_round_trip() { +fn test_hyperopt_22d_round_trip() { use ml::hyperopt::adapters::dqn::DQNParams; use ml::hyperopt::traits::ParameterSpace; - let mut params = DQNParams::default(); - params.cql_alpha = 0.25; - + let params = DQNParams::default(); let continuous = params.to_continuous(); let bounds = DQNParams::continuous_bounds(); - assert_eq!(continuous.len(), bounds.len(), "to_continuous length should match bounds"); + assert_eq!(continuous.len(), bounds.len(), + "to_continuous length ({}) should match bounds ({})", continuous.len(), bounds.len()); let reconstructed = DQNParams::from_continuous(&continuous).expect("from_continuous should succeed"); - let diff = (reconstructed.cql_alpha - 0.25).abs(); + // cql_alpha is fixed at default in 22D space + let diff = (reconstructed.cql_alpha - params.cql_alpha).abs(); assert!( diff < 0.01, - "cql_alpha should round-trip: expected 0.25, got {} (diff={})", - reconstructed.cql_alpha, diff + "cql_alpha should preserve default: expected {}, got {} (diff={})", + params.cql_alpha, reconstructed.cql_alpha, diff ); }