rustorch 0.6.29

Production-ready PyTorch-compatible deep learning library in Rust with special mathematical functions (gamma, Bessel, error functions), statistical distributions, Fourier transforms (FFT/RFFT), matrix decomposition (SVD/QR/LU/eigenvalue), automatic differentiation, neural networks, computer vision transforms, complete GPU acceleration (CUDA/Metal/OpenCL), SIMD optimizations, parallel processing, WebAssembly browser support, comprehensive distributed learning support, and performance validation
Documentation
//! f32統一ハイブリッド実行システム
//! f32 Unified Hybrid Execution System

#[cfg(target_os = "macos")]
use crate::hybrid_f32::gpu::{
    F32CoreMLExecutor, F32MetalExecutor, F32UnifiedGPUContext, GPUDevice,
};

use crate::error::RusTorchResult;
#[cfg(not(target_os = "macos"))]
use crate::hybrid_f32::gpu::{F32UnifiedGPUContext, GPUDevice};
use crate::hybrid_f32::tensor::core::F32Tensor;
use crate::hybrid_f32::ExperimentResults;
use std::time::Instant;

/// f32統一ハイブリッド実行エンジン
/// f32 Unified Hybrid Execution Engine
#[derive(Debug)]
pub struct F32HybridExecutor {
    gpu_context: F32UnifiedGPUContext,
    device_selector: F32DeviceSelector,
    performance_monitor: PerformanceMonitor,
}

impl F32HybridExecutor {
    /// 新しいハイブリッド実行エンジンを作成
    /// Create new hybrid execution engine
    pub fn new() -> RusTorchResult<Self> {
        crate::hybrid_f32_experimental!();

        let gpu_context = F32UnifiedGPUContext::new();
        let device_selector = F32DeviceSelector::new();
        let performance_monitor = PerformanceMonitor::new();

        println!("🚀 F32 Unified Hybrid Executor initialized");
        println!("  🔍 Detecting available devices...");

        Ok(Self {
            gpu_context,
            device_selector,
            performance_monitor,
        })
    }

    /// システム初期化
    /// Initialize system
    pub fn initialize(&mut self) -> RusTorchResult<()> {
        let available_devices = self.gpu_context.detect_available_devices();

        println!("📊 Available devices:");
        for (device, info) in &available_devices {
            println!(
                "  {:?}: {} ({:.1} TFLOPS f32)",
                device, info.device_name, info.estimated_tflops_f32
            );
        }

        self.device_selector
            .update_device_capabilities(available_devices);

        println!("✅ F32 Hybrid system initialized successfully");
        Ok(())
    }

    /// 統一実行(変換コストなし)
    /// Unified execution (no conversion cost)
    pub fn execute_matmul(
        &mut self,
        a: &F32Tensor,
        b: &F32Tensor,
    ) -> RusTorchResult<(F32Tensor, ExperimentResults)> {
        crate::hybrid_f32_experimental!();

        let start_time = Instant::now();

        // 最適デバイス選択
        let operation = F32Operation::MatMul {
            size_a: a.shape().to_vec(),
            size_b: b.shape().to_vec(),
        };
        let optimal_device = self.device_selector.select_optimal_device(&operation)?;

        println!("🎯 Selected device: {:?}", optimal_device);

        // デバイス初期化(必要に応じて)
        self.gpu_context.initialize_device(optimal_device.clone())?;

        // 統一実行
        let result = match optimal_device {
            GPUDevice::Metal(device_id) => {
                println!("⚡ Executing on Metal GPU {} (f32 direct)", device_id);
                self.execute_metal_f32(a, b)?
            }
            GPUDevice::CoreML(device_id) => {
                println!("🧠 Executing on Neural Engine {} (f32 direct)", device_id);
                self.execute_coreml_f32(a, b)?
            }
            GPUDevice::CPU => {
                println!("💻 Executing on CPU (f32 direct)");
                self.execute_cpu_f32(a, b)?
            }
        };

        let execution_time = start_time.elapsed();

        // 実験結果を記録
        let mut experiment_results = ExperimentResults::new();
        experiment_results.total_execution_time = execution_time;
        experiment_results.conversion_cost_reduction = 100.0; // 変換コスト完全削除

        self.performance_monitor
            .record_execution(&operation, execution_time, &optimal_device);

        println!("✅ Execution completed in {:?}", execution_time);
        println!("📊 Conversion cost reduction: 100% (zero conversion overhead)");

        Ok((result, experiment_results))
    }

    /// Metal f32実行
    /// Metal f32 execution
    fn execute_metal_f32(&self, a: &F32Tensor, b: &F32Tensor) -> RusTorchResult<F32Tensor> {
        self.gpu_context.execute_matmul(a, b)
    }

    /// CoreML f32実行
    /// CoreML f32 execution
    fn execute_coreml_f32(&self, a: &F32Tensor, b: &F32Tensor) -> RusTorchResult<F32Tensor> {
        self.gpu_context.execute_matmul(a, b)
    }

    /// CPU f32実行
    /// CPU f32 execution
    fn execute_cpu_f32(&self, a: &F32Tensor, b: &F32Tensor) -> RusTorchResult<F32Tensor> {
        a.matmul(b)
    }

    /// パフォーマンス統計を取得
    /// Get performance statistics
    pub fn get_performance_stats(&self) -> PerformanceStats {
        self.performance_monitor.get_stats()
    }
}

/// f32専用デバイス選択器
/// f32-specific device selector
#[derive(Debug)]
pub struct F32DeviceSelector {
    device_capabilities: Vec<(GPUDevice, super::gpu::DevicePerformanceInfo)>,
    selection_strategy: SelectionStrategy,
}

#[derive(Debug, Clone)]
pub enum SelectionStrategy {
    Performance,     // 最高性能優先
    PowerEfficiency, // 電力効率優先
    Adaptive,        // 適応的選択
}

impl F32DeviceSelector {
    pub fn new() -> Self {
        Self {
            device_capabilities: Vec::new(),
            selection_strategy: SelectionStrategy::Adaptive,
        }
    }

    pub fn update_device_capabilities(
        &mut self,
        capabilities: Vec<(GPUDevice, super::gpu::DevicePerformanceInfo)>,
    ) {
        self.device_capabilities = capabilities;
    }

    /// 最適デバイス選択(f32専用)
    /// Select optimal device (f32-specific)
    pub fn select_optimal_device(&self, operation: &F32Operation) -> RusTorchResult<GPUDevice> {
        match operation {
            F32Operation::MatMul { size_a, size_b } => {
                let total_elements =
                    size_a.iter().product::<usize>() + size_b.iter().product::<usize>();

                match total_elements {
                    // 大規模線形代数 → Metal GPU
                    size if size > 50000 => Ok(GPUDevice::Metal(0)),
                    // 中規模 → Neural Engine(f32でも効率的)
                    size if size > 1000 => Ok(GPUDevice::CoreML(0)),
                    // 小規模 → CPU
                    _ => Ok(GPUDevice::CPU),
                }
            }
            F32Operation::Conv2D { .. } => {
                // 畳み込み演算はNeural Engine優先
                Ok(GPUDevice::CoreML(0))
            }
            F32Operation::Activation { .. } => {
                // 活性化関数はNeural Engine最適
                Ok(GPUDevice::CoreML(0))
            }
        }
    }
}

/// f32操作タイプ
/// f32 operation types
#[derive(Debug, Clone)]
pub enum F32Operation {
    MatMul {
        size_a: Vec<usize>,
        size_b: Vec<usize>,
    },
    Conv2D {
        input_shape: Vec<usize>,
        kernel_shape: Vec<usize>,
    },
    Activation {
        input_shape: Vec<usize>,
    },
}

/// パフォーマンス監視
/// Performance monitoring
#[derive(Debug)]
pub struct PerformanceMonitor {
    execution_history: Vec<ExecutionRecord>,
    total_operations: usize,
    total_conversion_cost_saved: std::time::Duration,
}

#[derive(Debug, Clone)]
pub struct ExecutionRecord {
    pub operation: String,
    pub device: GPUDevice,
    pub execution_time: std::time::Duration,
    pub timestamp: Instant,
}

#[derive(Debug, Clone)]
pub struct PerformanceStats {
    pub total_operations: usize,
    pub average_execution_time: std::time::Duration,
    pub conversion_cost_savings: std::time::Duration,
    pub device_usage: std::collections::HashMap<String, usize>,
}

impl PerformanceMonitor {
    pub fn new() -> Self {
        Self {
            execution_history: Vec::new(),
            total_operations: 0,
            total_conversion_cost_saved: std::time::Duration::from_secs(0),
        }
    }

    pub fn record_execution(
        &mut self,
        operation: &F32Operation,
        execution_time: std::time::Duration,
        device: &GPUDevice,
    ) {
        let operation_name = match operation {
            F32Operation::MatMul { .. } => "matmul",
            F32Operation::Conv2D { .. } => "conv2d",
            F32Operation::Activation { .. } => "activation",
        };

        let record = ExecutionRecord {
            operation: operation_name.to_string(),
            device: device.clone(),
            execution_time,
            timestamp: Instant::now(),
        };

        self.execution_history.push(record);
        self.total_operations += 1;

        // 推定変換コスト節約(10-30%の実行時間相当)
        let estimated_conversion_cost = execution_time.mul_f64(0.2); // 20%推定
        self.total_conversion_cost_saved += estimated_conversion_cost;
    }

    pub fn get_stats(&self) -> PerformanceStats {
        let mut device_usage = std::collections::HashMap::new();
        let total_time: std::time::Duration = self
            .execution_history
            .iter()
            .map(|record| {
                let device_name = match &record.device {
                    GPUDevice::CPU => "CPU".to_string(),
                    GPUDevice::Metal(id) => format!("Metal({})", id),
                    GPUDevice::CoreML(id) => format!("CoreML({})", id),
                };
                *device_usage.entry(device_name).or_insert(0) += 1;
                record.execution_time
            })
            .sum();

        let average_time = if self.total_operations > 0 {
            total_time / self.total_operations as u32
        } else {
            std::time::Duration::from_secs(0)
        };

        PerformanceStats {
            total_operations: self.total_operations,
            average_execution_time: average_time,
            conversion_cost_savings: self.total_conversion_cost_saved,
            device_usage,
        }
    }
}

impl Default for F32HybridExecutor {
    fn default() -> Self {
        Self::new().expect("Failed to create F32HybridExecutor")
    }
}

impl Default for F32DeviceSelector {
    fn default() -> Self {
        Self::new()
    }
}

impl Default for PerformanceMonitor {
    fn default() -> Self {
        Self::new()
    }
}