use std::fmt::Debug;
use crate::core::error::{Error, Result};
use crate::series::base::Series;
pub trait SeriesGpuExt<T: Debug + Clone> {
fn gpu_accelerate(&self) -> Result<Self>
where
Self: Sized;
fn gpu_sum(&self) -> Result<T>;
fn gpu_mean(&self) -> Result<T>;
fn gpu_std(&self) -> Result<T>;
fn gpu_corr(&self, other: &Self) -> Result<f64>
where
Self: Sized;
}
impl SeriesGpuExt<f64> for Series<f64> {
fn gpu_accelerate(&self) -> Result<Self> {
Err(Error::NotImplemented(
"GPU acceleration for Series not implemented (no real CUDA kernel)".into(),
))
}
fn gpu_sum(&self) -> Result<f64> {
Ok(self.sum())
}
fn gpu_mean(&self) -> Result<f64> {
self.mean()
}
fn gpu_std(&self) -> Result<f64> {
let clean: Vec<f64> = self
.values()
.iter()
.copied()
.filter(|v| !v.is_nan())
.collect();
crate::stats::descriptive::std_dev(&clean, 1)
}
fn gpu_corr(&self, other: &Self) -> Result<f64> {
if self.len() != other.len() {
return Err(Error::DimensionMismatch(format!(
"Series lengths differ: {} vs {}",
self.len(),
other.len()
)));
}
let (xs, ys): (Vec<f64>, Vec<f64>) = self
.values()
.iter()
.zip(other.values().iter())
.filter(|(&x, &y)| !x.is_nan() && !y.is_nan())
.map(|(&x, &y)| (x, y))
.unzip();
crate::stats::descriptive::pearson_correlation(&xs, &ys)
}
}