1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
use std::{fmt::Debug, str::FromStr};

/// The neutral elements of addition and multiplication are zero and one, respectively.
/// An implementation is provided for all types that implement `From<u8> + PartialEq`.
pub trait NeutralElts: PartialEq {
    fn zero() -> Self;
    fn one() -> Self;
}

impl<T> NeutralElts for T
where
    T: From<u8> + PartialEq,
{
    fn zero() -> Self {
        T::from(0)
    }
    fn one() -> Self {
        T::from(1)
    }
}

/// Gathers `Clone`, `FromStr`, `Debug`, and `Default` in one trait.
/// Every type that is used as value needs to implement at least this.
pub trait DataType: Clone + FromStr + Debug + Default {}
impl<T: Clone + FromStr + Debug + Default> DataType for T {}

/// [`DataType`]s of expressions that are differentiable need to implement
/// additionally `From<f32>`, `PartialEq`, and [`NeutralElts`]. Vice-versa,
/// if you have an expression with a datatype that implements [`DiffDataType`],
/// partial derivatives of that expression can be computed.
#[cfg(feature = "partial")]
pub trait DiffDataType: DataType + From<f32> + NeutralElts {}
#[cfg(feature = "partial")]
impl<T: DataType + From<f32> + NeutralElts> DiffDataType for T {}