X-Git-Url: https://git.libre-soc.org/?p=vector-math.git;a=blobdiff_plain;f=src%2Ftraits.rs;h=1877c21f1cb7d1fde0c73114f7170a4f0261d1a8;hp=6555016d98793e1c70b8715fe85e5f3f3a5878cf;hb=ba67f8a36240e8ee2e95bb79aa7a58ae77577197;hpb=ad217eb300ff1d610689c9ebe5b06e94b659a508 diff --git a/src/traits.rs b/src/traits.rs index 6555016..1877c21 100644 --- a/src/traits.rs +++ b/src/traits.rs @@ -1,4 +1,4 @@ -use crate::{f16::F16, ieee754::FloatEncoding, scalar::Scalar}; +use crate::{f16::F16, ieee754::FloatEncoding}; use core::ops::{ Add, AddAssign, BitAnd, BitAndAssign, BitOr, BitOrAssign, BitXor, BitXorAssign, Div, DivAssign, Mul, MulAssign, Neg, Not, Rem, RemAssign, Shl, ShlAssign, Shr, ShrAssign, Sub, SubAssign, @@ -19,37 +19,47 @@ pub trait Make: Copy { fn make(ctx: Self::Context, v: Self::Prim) -> Self; } +pub trait ConvertFrom: Sized { + fn cvt_from(v: T) -> Self; +} + +impl ConvertFrom for T { + fn cvt_from(v: T) -> Self { + v + } +} + pub trait ConvertTo { fn to(self) -> T; } -impl ConvertTo for T { +impl> ConvertTo for F { fn to(self) -> T { - self + T::cvt_from(self) } } -macro_rules! impl_convert_to_using_as { +macro_rules! impl_convert_from_using_as { ($first:ident $(, $ty:ident)*) => { $( - impl ConvertTo<$first> for $ty { - fn to(self) -> $first { - self as $first + impl ConvertFrom<$first> for $ty { + fn cvt_from(v: $first) -> Self { + v as _ } } - impl ConvertTo<$ty> for $first { - fn to(self) -> $ty { - self as $ty + impl ConvertFrom<$ty> for $first { + fn cvt_from(v: $ty) -> Self { + v as _ } } )* - impl_convert_to_using_as![$($ty),*]; + impl_convert_from_using_as![$($ty),*]; }; () => { }; } -impl_convert_to_using_as![u8, i8, u16, i16, u32, i32, u64, i64, f32, f64]; +impl_convert_from_using_as![u8, i8, u16, i16, u32, i32, u64, i64, f32, f64]; pub trait Number: Compare @@ -126,61 +136,14 @@ pub trait UInt: Int {} pub trait SInt: Int + Neg {} -macro_rules! impl_int { - ($ty:ident) => { - impl Int for $ty { - fn leading_zeros(self) -> Self { - self.leading_zeros() as Self - } - fn leading_ones(self) -> Self { - self.leading_ones() as Self - } - fn trailing_zeros(self) -> Self { - self.trailing_zeros() as Self - } - fn trailing_ones(self) -> Self { - self.trailing_ones() as Self - } - fn count_zeros(self) -> Self { - self.count_zeros() as Self - } - fn count_ones(self) -> Self { - self.count_ones() as Self - } - } - }; -} - -macro_rules! impl_uint { - ($($ty:ident),*) => { - $( - impl_int!($ty); - impl UInt for $ty {} - )* - }; -} - -impl_uint![u8, u16, u32, u64]; - -macro_rules! impl_sint { - ($($ty:ident),*) => { - $( - impl_int!($ty); - impl SInt for $ty {} - )* - }; -} - -impl_sint![i8, i16, i32, i64]; - pub trait Float: Number + Neg { - type FloatEncoding: FloatEncoding + Make::Prim>; + type FloatEncoding: FloatEncoding + From<::Prim> + Into<::Prim>; type BitsType: UInt - + Make::BitsType> + + Make::BitsType> + ConvertTo + Compare; type SignedBitsType: SInt - + Make::SignedBitsType> + + Make::SignedBitsType> + ConvertTo + Compare; fn abs(self) -> Self; @@ -246,85 +209,12 @@ pub trait Float: Number + Neg { } } -macro_rules! impl_float { - ($ty:ty, $bits:ty, $signed_bits:ty) => { - impl Float for $ty { - type FloatEncoding = $ty; - type BitsType = $bits; - type SignedBitsType = $signed_bits; - fn abs(self) -> Self { - #[cfg(feature = "std")] - return self.abs(); - #[cfg(not(feature = "std"))] - todo!(); - } - fn trunc(self) -> Self { - #[cfg(feature = "std")] - return self.trunc(); - #[cfg(not(feature = "std"))] - todo!(); - } - fn ceil(self) -> Self { - #[cfg(feature = "std")] - return self.ceil(); - #[cfg(not(feature = "std"))] - todo!(); - } - fn floor(self) -> Self { - #[cfg(feature = "std")] - return self.floor(); - #[cfg(not(feature = "std"))] - todo!(); - } - fn round(self) -> Self { - #[cfg(feature = "std")] - return self.round(); - #[cfg(not(feature = "std"))] - todo!(); - } - #[cfg(feature = "fma")] - fn fma(self, a: Self, b: Self) -> Self { - self.mul_add(a, b) - } - fn is_nan(self) -> Self::Bool { - self.is_nan() - } - fn is_infinite(self) -> Self::Bool { - self.is_infinite() - } - fn is_finite(self) -> Self::Bool { - self.is_finite() - } - fn from_bits(v: Self::BitsType) -> Self { - <$ty>::from_bits(v) - } - fn to_bits(self) -> Self::BitsType { - self.to_bits() - } - } - }; -} - -impl_float!(f32, u32, i32); -impl_float!(f64, u64, i64); - pub trait Bool: Make + BitOps {} -impl Bool for bool {} - pub trait Select: Bool { fn select(self, true_v: T, false_v: T) -> T; } -impl Select for bool { - fn select(self, true_v: T, false_v: T) -> T { - if self { - true_v - } else { - false_v - } - } -} pub trait Compare: Make { type Bool: Bool + Select; fn eq(self, rhs: Self) -> Self::Bool; @@ -334,33 +224,3 @@ pub trait Compare: Make { fn le(self, rhs: Self) -> Self::Bool; fn ge(self, rhs: Self) -> Self::Bool; } - -macro_rules! impl_compare_using_partial_cmp { - ($($ty:ty),*) => { - $( - impl Compare for $ty { - type Bool = bool; - fn eq(self, rhs: Self) -> Self::Bool { - self == rhs - } - fn ne(self, rhs: Self) -> Self::Bool { - self != rhs - } - fn lt(self, rhs: Self) -> Self::Bool { - self < rhs - } - fn gt(self, rhs: Self) -> Self::Bool { - self > rhs - } - fn le(self, rhs: Self) -> Self::Bool { - self <= rhs - } - fn ge(self, rhs: Self) -> Self::Bool { - self >= rhs - } - } - )* - }; -} - -impl_compare_using_partial_cmp![bool, u8, i8, u16, i16, F16, u32, i32, f32, u64, i64, f64];