intentional/
cast.rs

1/// A trait for casting a type to another type using the `as` operator.
2pub trait CastInto<To> {
3    /// Returns `self as To`.
4    fn cast_into(self) -> To;
5}
6
7/// A trait for casting a type from another type using the `as` operator.
8pub trait CastFrom<From> {
9    /// Returns `from as Self`.
10    fn from_cast(from: From) -> Self;
11}
12
13impl<A, B> CastInto<A> for B
14where
15    A: CastFrom<B>,
16{
17    #[inline]
18    fn cast_into(self) -> A {
19        A::from_cast(self)
20    }
21}
22
23impl<A> CastFrom<A> for A {
24    #[inline]
25    fn from_cast(from: A) -> Self {
26        from
27    }
28}
29
30/// Allows casting from this type to other types using
31/// [`CastFrom`]/[`CastInto`].
32pub trait Cast: Sized {
33    /// Casts `self` to the `To` type. This may be a lossy operation.
34    fn cast<To: CastFrom<Self>>(self) -> To;
35}
36
37impl<A> Cast for A {
38    #[inline]
39    fn cast<To: CastFrom<Self>>(self) -> To {
40        To::from_cast(self)
41    }
42}
43
44macro_rules! impl_cast_from {
45    ($from:ident, [$($to:ident),+]) => {
46        $(impl_cast_from!($from, $to);)+
47    };
48    ($from:ident, $to:ident) => {
49        impl CastFrom<$from> for $to {
50            #[doc = "```rust\n"]
51            #[doc = "# use intentional::Cast;\n"]
52            #[doc = concat!("let casted: ", stringify!($to), " = 1_", stringify!($from), ".cast();\n")]
53            #[doc = "```\n"]
54            #[inline]
55            fn from_cast(from: $from) -> Self {
56                from as $to
57            }
58        }
59    };
60}
61
62impl_cast_from!(u8, i8);
63impl_cast_from!(i8, [u8, usize]);
64impl_cast_from!(u16, [u8, i8, i16]);
65impl_cast_from!(i16, [u8, i8, u16, usize]);
66impl_cast_from!(u32, [f32, usize, isize, u8, i8, u16, i16, i32]);
67impl_cast_from!(i32, [f32, usize, isize, u8, i8, u16, i16, u32]);
68impl_cast_from!(
69    u64,
70    [f32, f64, usize, isize, u8, i8, u16, i16, u32, i32, i64]
71);
72impl_cast_from!(
73    i64,
74    [f32, f64, usize, isize, u8, i8, u16, i16, u32, i32, u64]
75);
76impl_cast_from!(
77    u128,
78    [f32, f64, usize, isize, u8, i8, u16, i16, u32, i32, u64, i64, i128]
79);
80impl_cast_from!(
81    i128,
82    [f32, f64, usize, isize, u8, i8, u16, i16, u32, i32, u64, i64, u128]
83);
84impl_cast_from!(
85    isize,
86    [f32, f64, usize, u8, i8, u16, i16, u32, i32, u64, i64, u128, i128]
87);
88impl_cast_from!(
89    usize,
90    [f32, f64, isize, u8, i8, u16, i16, u32, i32, u64, i64, u128, i128]
91);
92impl_cast_from!(
93    f32,
94    [usize, isize, u8, i8, u16, i16, u32, i32, u64, i64, u128, i128]
95);
96impl_cast_from!(
97    f64,
98    [usize, isize, u8, i8, u16, i16, u32, i32, u64, i64, u128, i128, f32]
99);