use std::borrow::Cow;
use std::marker::PhantomData;
use num_complex::Complex64;
pub trait IntoAxis {
type Point: Copy;
fn into_axis(points: &[Self::Point]) -> Vec<Complex64>;
}
#[derive(Debug, Clone, Copy)]
pub struct Axis<'a, A: IntoAxis> {
pub points: &'a [A::Point],
_marker: PhantomData<A>,
}
impl<'a, A: IntoAxis> Axis<'a, A> {
pub fn to_complex(&self) -> Vec<Complex64> {
A::into_axis(self.points)
}
pub fn len(&self) -> usize {
self.points.len()
}
pub fn is_empty(&self) -> bool {
self.points.is_empty()
}
}
pub struct ComplexAxis;
impl IntoAxis for ComplexAxis {
type Point = Complex64;
fn into_axis(points: &[Complex64]) -> Vec<Complex64> {
points.to_vec()
}
}
pub struct Hz;
impl IntoAxis for Hz {
type Point = f64;
fn into_axis(points: &[f64]) -> Vec<Complex64> {
points
.iter()
.map(|f| Complex64::new(0.0, 2.0 * std::f64::consts::PI * f))
.collect()
}
}
pub struct RadPerSec;
impl IntoAxis for RadPerSec {
type Point = f64;
fn into_axis(points: &[f64]) -> Vec<Complex64> {
points.iter().map(|w| Complex64::new(0.0, *w)).collect()
}
}
pub struct RealAxis;
impl IntoAxis for RealAxis {
type Point = f64;
fn into_axis(points: &[f64]) -> Vec<Complex64> {
points.iter().map(|x| Complex64::new(*x, 0.0)).collect()
}
}
pub fn hz(freq: &[f64]) -> Axis<'_, Hz> {
Axis {
points: freq,
_marker: PhantomData,
}
}
pub fn rad(omega: &[f64]) -> Axis<'_, RadPerSec> {
Axis {
points: omega,
_marker: PhantomData,
}
}
pub fn real(x: &[f64]) -> Axis<'_, RealAxis> {
Axis {
points: x,
_marker: PhantomData,
}
}
pub fn complex(s: &[Complex64]) -> Axis<'_, ComplexAxis> {
Axis {
points: s,
_marker: PhantomData,
}
}
pub fn c(re: f64, im: f64) -> Complex64 {
Complex64::new(re, im)
}
pub trait AsComplexAxis {
fn as_complex_axis(&self) -> Cow<'_, [Complex64]>;
}
impl<'a> AsComplexAxis for &'a [Complex64] {
fn as_complex_axis(&self) -> Cow<'a, [Complex64]> {
Cow::Borrowed(self)
}
}
impl<'a> AsComplexAxis for &'a Vec<Complex64> {
fn as_complex_axis(&self) -> Cow<'a, [Complex64]> {
Cow::Borrowed(self.as_slice())
}
}
impl<'a, A: IntoAxis> AsComplexAxis for Axis<'a, A> {
fn as_complex_axis(&self) -> Cow<'a, [Complex64]> {
Cow::Owned(self.to_complex())
}
}