#[non_exhaustive]
#[derive(Debug, Clone, Copy, PartialEq, Eq, Default)]
pub enum NormMode {
#[default]
None,
Ortho,
Forward,
}
#[derive(Debug, Clone)]
pub struct NdimFftConfig {
pub norm: NormMode,
pub threads: usize,
pub tile_size: usize,
}
impl Default for NdimFftConfig {
fn default() -> Self {
NdimFftConfig {
norm: NormMode::default(),
threads: 0,
tile_size: 64,
}
}
}
#[derive(Debug, Clone)]
pub struct NdimFftResult {
pub data: Vec<(f64, f64)>,
pub shape: Vec<usize>,
}
impl NdimFftResult {
pub fn new(data: Vec<(f64, f64)>, shape: Vec<usize>) -> Option<Self> {
let expected: usize = shape.iter().product();
if data.len() != expected {
return None;
}
Some(NdimFftResult { data, shape })
}
#[inline]
pub fn len(&self) -> usize {
self.data.len()
}
#[inline]
pub fn is_empty(&self) -> bool {
self.data.is_empty()
}
}
#[derive(Debug, Clone)]
pub struct FftPlan {
pub shape: Vec<usize>,
pub strides: Vec<usize>,
pub twiddle_tables: Vec<Vec<(f64, f64)>>,
}
impl FftPlan {
pub fn build(shape: &[usize]) -> Self {
let ndim = shape.len();
let mut strides = vec![1usize; ndim];
for i in (0..ndim.saturating_sub(1)).rev() {
strides[i] = strides[i + 1] * shape[i + 1];
}
let twiddle_tables: Vec<Vec<(f64, f64)>> = shape
.iter()
.map(|&n| crate::ndim_fft::mixed_radix::compute_twiddles(n))
.collect();
FftPlan {
shape: shape.to_vec(),
strides,
twiddle_tables,
}
}
}
#[derive(Debug, Clone, Default)]
pub enum FftAxis {
#[default]
All,
Selected(Vec<usize>),
}