use chrono::{DateTime, Utc};
use serde::{Deserialize, Serialize};
use std::collections::HashMap;
#[derive(Debug, Clone, Serialize, Deserialize)]
pub struct CounterfactualResult {
pub timestamp: DateTime<Utc>,
pub counterfactuals: Vec<Counterfactual>,
pub quality_metrics: CounterfactualQualityMetrics,
pub feature_sensitivity: FeatureSensitivityAnalysis,
pub decision_boundary: DecisionBoundaryAnalysis,
pub actionable_insights: Vec<ActionableInsight>,
}
#[derive(Debug, Clone, Serialize, Deserialize)]
pub struct Counterfactual {
pub id: String,
pub original_instance: HashMap<String, f64>,
pub counterfactual_instance: HashMap<String, f64>,
pub changed_features: Vec<FeatureChange>,
pub original_prediction: f64,
pub counterfactual_prediction: f64,
pub distance: f64,
pub plausibility: f64,
pub actionability: f64,
}
#[derive(Debug, Clone, Serialize, Deserialize)]
pub struct FeatureChange {
pub feature_name: String,
pub original_value: f64,
pub new_value: f64,
pub change_magnitude: f64,
pub change_direction: ChangeDirection,
pub change_cost: f64,
}
#[derive(Debug, Clone, Serialize, Deserialize)]
pub enum ChangeDirection {
Increase,
Decrease,
Categorical,
}
#[derive(Debug, Clone, Serialize, Deserialize)]
pub struct CounterfactualQualityMetrics {
pub avg_distance: f64,
pub avg_plausibility: f64,
pub avg_actionability: f64,
pub diversity: f64,
pub coverage: f64,
pub sparsity: f64,
}
#[derive(Debug, Clone, Serialize, Deserialize)]
pub struct FeatureSensitivityAnalysis {
pub feature_sensitivities: HashMap<String, f64>,
pub most_sensitive: Vec<String>,
pub least_sensitive: Vec<String>,
pub interaction_effects: Vec<InteractionEffect>,
pub threshold_analysis: ThresholdAnalysis,
}
#[derive(Debug, Clone, Serialize, Deserialize)]
pub struct InteractionEffect {
pub features: Vec<String>,
pub effect_magnitude: f64,
pub effect_type: InteractionEffectType,
}
#[derive(Debug, Clone, Serialize, Deserialize)]
pub enum InteractionEffectType {
Synergistic,
Antagonistic,
Independent,
}
#[derive(Debug, Clone, Serialize, Deserialize)]
pub struct ThresholdAnalysis {
pub feature_thresholds: HashMap<String, f64>,
pub threshold_confidence: HashMap<String, (f64, f64)>,
pub critical_features: Vec<String>,
pub robust_features: Vec<String>,
}
#[derive(Debug, Clone, Serialize, Deserialize)]
pub struct DecisionBoundaryAnalysis {
pub boundary_curvature: f64,
pub boundary_complexity: f64,
pub distance_to_boundary: f64,
pub crossing_points: Vec<BoundaryCrossingPoint>,
pub local_linearity: f64,
}
#[derive(Debug, Clone, Serialize, Deserialize)]
pub struct BoundaryCrossingPoint {
pub coordinates: HashMap<String, f64>,
pub distance: f64,
pub boundary_prediction: f64,
pub crossing_direction: Vec<f64>,
}
#[derive(Debug, Clone, Serialize, Deserialize)]
pub struct ActionableInsight {
pub description: String,
pub required_changes: Vec<FeatureChange>,
pub expected_outcome: f64,
pub confidence: f64,
pub difficulty: ImplementationDifficulty,
pub time_horizon: TimeHorizon,
}
#[derive(Debug, Clone, Serialize, Deserialize)]
pub enum ImplementationDifficulty {
Easy,
Moderate,
Hard,
VeryHard,
Impossible,
}
#[derive(Debug, Clone, Serialize, Deserialize)]
pub enum TimeHorizon {
Immediate,
ShortTerm,
MediumTerm,
LongTerm,
}