use super::rating::EloRating;

/// Calculate effective opponent rating for a player in doubles
/// This personalizes the rating adjustment based on partner strength
/// 
/// Formula: Effective Opponent = Opp1_rating + Opp2_rating - Teammate_rating
/// 
/// This makes intuitive sense:
/// - If opponents are strong, effective opponent rating is higher
/// - If your teammate is strong, effective opponent rating is lower (teammate helped)
/// - If your teammate is weak, effective opponent rating is higher (you did more work)
///
/// Returns: The effective opponent rating (in display scale, e.g., 1400-1600)
pub fn calculate_effective_opponent_rating(
    opponent1_rating: f64,
    opponent2_rating: f64,
    teammate_rating: f64,
) -> f64 {
    opponent1_rating + opponent2_rating - teammate_rating
}

/// Calculate effective opponent as an EloRating struct
pub fn calculate_effective_opponent(
    opponent1: &EloRating,
    opponent2: &EloRating,
    teammate: &EloRating,
) -> EloRating {
    let effective_rating = calculate_effective_opponent_rating(
        opponent1.rating,
        opponent2.rating,
        teammate.rating,
    );
    
    EloRating {
        rating: effective_rating,
    }
}

#[cfg(test)]
mod tests {
    use super::*;
    
    #[test]
    fn test_effective_opponent_equal_teams() {
        // Both teams equally matched
        // Opp1: 1500, Opp2: 1500, Teammate: 1500
        // Effective opponent = 1500 + 1500 - 1500 = 1500
        let eff = calculate_effective_opponent_rating(1500.0, 1500.0, 1500.0);
        assert!((eff - 1500.0).abs() < 0.001);
    }
    
    #[test]
    fn test_effective_opponent_strong_teammate() {
        // Strong teammates make it "easier" - lower effective opponent
        // Opp1: 1500, Opp2: 1500, Teammate: 1600
        // Effective opponent = 1500 + 1500 - 1600 = 1400
        let eff = calculate_effective_opponent_rating(1500.0, 1500.0, 1600.0);
        assert!((eff - 1400.0).abs() < 0.001);
    }
    
    #[test]
    fn test_effective_opponent_weak_teammate() {
        // Weak teammates make it "harder" - higher effective opponent
        // Opp1: 1500, Opp2: 1500, Teammate: 1400
        // Effective opponent = 1500 + 1500 - 1400 = 1600
        let eff = calculate_effective_opponent_rating(1500.0, 1500.0, 1400.0);
        assert!((eff - 1600.0).abs() < 0.001);
    }
    
    #[test]
    fn test_effective_opponent_struct() {
        let opp1 = EloRating { rating: 1500.0 };
        let opp2 = EloRating { rating: 1600.0 };
        let teammate = EloRating { rating: 1400.0 };
        
        let eff = calculate_effective_opponent(&opp1, &opp2, &teammate);
        
        // Rating: 1500 + 1600 - 1400 = 1700
        assert!((eff.rating - 1700.0).abs() < 0.001);
    }
}
