1use std::fmt::Debug;
11
12pub use strong_type_derive::StrongType;
14
15pub trait StrongType: Debug + PartialEq + PartialOrd + Clone {
17 type UnderlyingType;
18 type PrimitiveType;
19}
20
21#[doc(hidden)]
26pub mod delegation {
27 pub trait StrongTypeOps: Sized {
30 type Primitive: Copy;
31
32 fn to_primitive(self) -> Self::Primitive;
34
35 fn from_primitive(val: Self::Primitive) -> Self;
37 }
38
39 #[inline(never)]
45 pub fn delegate_add<T>(lhs: T, rhs: T) -> T
46 where
47 T: StrongTypeOps,
48 T::Primitive: std::ops::Add<Output = T::Primitive>,
49 {
50 T::from_primitive(lhs.to_primitive() + rhs.to_primitive())
51 }
52
53 #[inline(never)]
55 pub fn delegate_sub<T>(lhs: T, rhs: T) -> T
56 where
57 T: StrongTypeOps,
58 T::Primitive: std::ops::Sub<Output = T::Primitive>,
59 {
60 T::from_primitive(lhs.to_primitive() - rhs.to_primitive())
61 }
62
63 #[inline(never)]
65 pub fn delegate_mul<T>(lhs: T, rhs: T) -> T
66 where
67 T: StrongTypeOps,
68 T::Primitive: std::ops::Mul<Output = T::Primitive>,
69 {
70 T::from_primitive(lhs.to_primitive() * rhs.to_primitive())
71 }
72
73 #[inline(never)]
75 pub fn delegate_div<T>(lhs: T, rhs: T) -> T
76 where
77 T: StrongTypeOps,
78 T::Primitive: std::ops::Div<Output = T::Primitive>,
79 {
80 T::from_primitive(lhs.to_primitive() / rhs.to_primitive())
81 }
82
83 #[inline(never)]
85 pub fn delegate_rem<T>(lhs: T, rhs: T) -> T
86 where
87 T: StrongTypeOps,
88 T::Primitive: std::ops::Rem<Output = T::Primitive>,
89 {
90 T::from_primitive(lhs.to_primitive() % rhs.to_primitive())
91 }
92
93 #[inline(never)]
95 pub fn delegate_bitand<T>(lhs: T, rhs: T) -> T
96 where
97 T: StrongTypeOps,
98 T::Primitive: std::ops::BitAnd<Output = T::Primitive>,
99 {
100 T::from_primitive(lhs.to_primitive() & rhs.to_primitive())
101 }
102
103 #[inline(never)]
105 pub fn delegate_bitor<T>(lhs: T, rhs: T) -> T
106 where
107 T: StrongTypeOps,
108 T::Primitive: std::ops::BitOr<Output = T::Primitive>,
109 {
110 T::from_primitive(lhs.to_primitive() | rhs.to_primitive())
111 }
112
113 #[inline(never)]
115 pub fn delegate_bitxor<T>(lhs: T, rhs: T) -> T
116 where
117 T: StrongTypeOps,
118 T::Primitive: std::ops::BitXor<Output = T::Primitive>,
119 {
120 T::from_primitive(lhs.to_primitive() ^ rhs.to_primitive())
121 }
122
123 #[inline(never)]
129 pub fn delegate_neg<T>(val: T) -> T
130 where
131 T: StrongTypeOps,
132 T::Primitive: std::ops::Neg<Output = T::Primitive>,
133 {
134 T::from_primitive(-val.to_primitive())
135 }
136
137 #[inline(never)]
139 pub fn delegate_not<T>(val: T) -> T
140 where
141 T: StrongTypeOps,
142 T::Primitive: std::ops::Not<Output = T::Primitive>,
143 {
144 T::from_primitive(!val.to_primitive())
145 }
146
147 #[inline(never)]
153 pub fn delegate_shl<T, Rhs>(lhs: T, rhs: Rhs) -> T
154 where
155 T: StrongTypeOps,
156 T::Primitive: std::ops::Shl<Rhs, Output = T::Primitive>,
157 Rhs: Copy,
158 {
159 T::from_primitive(lhs.to_primitive() << rhs)
160 }
161
162 #[inline(never)]
164 pub fn delegate_shr<T, Rhs>(lhs: T, rhs: Rhs) -> T
165 where
166 T: StrongTypeOps,
167 T::Primitive: std::ops::Shr<Rhs, Output = T::Primitive>,
168 Rhs: Copy,
169 {
170 T::from_primitive(lhs.to_primitive() >> rhs)
171 }
172
173 #[inline(never)]
179 pub fn delegate_scalar_mul<T>(lhs: T, rhs: T::Primitive) -> T
180 where
181 T: StrongTypeOps,
182 T::Primitive: std::ops::Mul<Output = T::Primitive>,
183 {
184 T::from_primitive(lhs.to_primitive() * rhs)
185 }
186
187 #[inline(never)]
189 pub fn delegate_scalar_div<T>(lhs: T, rhs: T::Primitive) -> T
190 where
191 T: StrongTypeOps,
192 T::Primitive: std::ops::Div<Output = T::Primitive>,
193 {
194 T::from_primitive(lhs.to_primitive() / rhs)
195 }
196
197 #[inline(never)]
199 pub fn delegate_scalar_rem<T>(lhs: T, rhs: T::Primitive) -> T
200 where
201 T: StrongTypeOps,
202 T::Primitive: std::ops::Rem<Output = T::Primitive>,
203 {
204 T::from_primitive(lhs.to_primitive() % rhs)
205 }
206}