diff --git a/ml/src/trainers/dqn.rs b/ml/src/trainers/dqn.rs index 5d3fb8e1f..dc69afce9 100644 --- a/ml/src/trainers/dqn.rs +++ b/ml/src/trainers/dqn.rs @@ -3439,12 +3439,19 @@ impl DQNTrainer { normalized_features[3], // close log return (can be negative) ]; - // WAVE 16D: Extract technical indicators (121 features, indices 4-124) - // NOTE: Indices 125-127 are portfolio placeholders, replaced by PortfolioTracker below - let technical_indicators: Vec = normalized_features[4..125].to_vec(); + // 54-FEATURE ARCHITECTURE: Extract market features (indices 4-53) + // Features 0-3: OHLCV log returns (preserved above as price_features) + // Features 4-53: Technical indicators, Proxy OFI, time, statistical features + // Portfolio features added separately via PortfolioTracker below + let market_features: Vec = if normalized_features.len() >= 54 { + normalized_features[4..54].to_vec() + } else { + // Fallback for backward compatibility (225-feature vectors) + normalized_features[4..std::cmp::min(125, normalized_features.len())].to_vec() + }; - // Empty market features (all consolidated into technical_indicators) - let market_features = vec![]; + // Legacy technical_indicators for backward compatibility (empty for 54-feature) + let technical_indicators = vec![]; // BUG #36 FIX: Use NORMALIZED portfolio features to prevent Q-value explosion // @@ -3473,17 +3480,16 @@ impl DQNTrainer { vec![0.0, 0.0, 0.0] // Fallback if no price provided }; - // WAVE 8.3 FIX: Extract regime detection features (97 features, indices 128-224) - // Migration 045 added regime features: - // - 12 microstructure features (indices 128-139) - // - 85 regime detection features (indices 140-224) - // Indices 125-127 are portfolio placeholders (populated above by PortfolioTracker) - // Total state dimension: 4 (price) + 121 (technical) + 3 (portfolio) + 12 (microstructure) + 85 (regime) = 225 + // 54-FEATURE ARCHITECTURE: No regime features (removed for feature reduction) + // 54 features = 4 (OHLCV) + 50 (market/technical/OFI/statistical) + // Portfolio features added separately via PortfolioTracker (3 features) + // Regime detection removed as part of 225→54 feature reduction (indices 211, 203 out of bounds) let regime_features: Vec = if normalized_features.len() >= 225 { + // Legacy 225-feature support normalized_features[128..225].to_vec() } else { - // Fallback for tests using 128-dim feature vectors (old format) - vec![0.0; 97] + // 54-feature architecture: no regime features + vec![] }; // Use from_normalized() to preserve sign information