int.rs 9.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383
  1. use core::ops::{BitAnd, BitOr, BitXor, Not, Shl, Shr};
  2. use bounds::Bounded;
  3. use ops::checked::*;
  4. use ops::saturating::Saturating;
  5. use {Num, NumCast};
  6. pub trait PrimInt:
  7. Sized
  8. + Copy
  9. + Num
  10. + NumCast
  11. + Bounded
  12. + PartialOrd
  13. + Ord
  14. + Eq
  15. + Not<Output = Self>
  16. + BitAnd<Output = Self>
  17. + BitOr<Output = Self>
  18. + BitXor<Output = Self>
  19. + Shl<usize, Output = Self>
  20. + Shr<usize, Output = Self>
  21. + CheckedAdd<Output = Self>
  22. + CheckedSub<Output = Self>
  23. + CheckedMul<Output = Self>
  24. + CheckedDiv<Output = Self>
  25. + Saturating
  26. {
  27. /// Returns the number of ones in the binary representation of `self`.
  28. ///
  29. /// # Examples
  30. ///
  31. /// ```
  32. /// use num_traits::PrimInt;
  33. ///
  34. /// let n = 0b01001100u8;
  35. ///
  36. /// assert_eq!(n.count_ones(), 3);
  37. /// ```
  38. fn count_ones(self) -> u32;
  39. /// Returns the number of zeros in the binary representation of `self`.
  40. ///
  41. /// # Examples
  42. ///
  43. /// ```
  44. /// use num_traits::PrimInt;
  45. ///
  46. /// let n = 0b01001100u8;
  47. ///
  48. /// assert_eq!(n.count_zeros(), 5);
  49. /// ```
  50. fn count_zeros(self) -> u32;
  51. /// Returns the number of leading zeros in the binary representation
  52. /// of `self`.
  53. ///
  54. /// # Examples
  55. ///
  56. /// ```
  57. /// use num_traits::PrimInt;
  58. ///
  59. /// let n = 0b0101000u16;
  60. ///
  61. /// assert_eq!(n.leading_zeros(), 10);
  62. /// ```
  63. fn leading_zeros(self) -> u32;
  64. /// Returns the number of trailing zeros in the binary representation
  65. /// of `self`.
  66. ///
  67. /// # Examples
  68. ///
  69. /// ```
  70. /// use num_traits::PrimInt;
  71. ///
  72. /// let n = 0b0101000u16;
  73. ///
  74. /// assert_eq!(n.trailing_zeros(), 3);
  75. /// ```
  76. fn trailing_zeros(self) -> u32;
  77. /// Shifts the bits to the left by a specified amount amount, `n`, wrapping
  78. /// the truncated bits to the end of the resulting integer.
  79. ///
  80. /// # Examples
  81. ///
  82. /// ```
  83. /// use num_traits::PrimInt;
  84. ///
  85. /// let n = 0x0123456789ABCDEFu64;
  86. /// let m = 0x3456789ABCDEF012u64;
  87. ///
  88. /// assert_eq!(n.rotate_left(12), m);
  89. /// ```
  90. fn rotate_left(self, n: u32) -> Self;
  91. /// Shifts the bits to the right by a specified amount amount, `n`, wrapping
  92. /// the truncated bits to the beginning of the resulting integer.
  93. ///
  94. /// # Examples
  95. ///
  96. /// ```
  97. /// use num_traits::PrimInt;
  98. ///
  99. /// let n = 0x0123456789ABCDEFu64;
  100. /// let m = 0xDEF0123456789ABCu64;
  101. ///
  102. /// assert_eq!(n.rotate_right(12), m);
  103. /// ```
  104. fn rotate_right(self, n: u32) -> Self;
  105. /// Shifts the bits to the left by a specified amount amount, `n`, filling
  106. /// zeros in the least significant bits.
  107. ///
  108. /// This is bitwise equivalent to signed `Shl`.
  109. ///
  110. /// # Examples
  111. ///
  112. /// ```
  113. /// use num_traits::PrimInt;
  114. ///
  115. /// let n = 0x0123456789ABCDEFu64;
  116. /// let m = 0x3456789ABCDEF000u64;
  117. ///
  118. /// assert_eq!(n.signed_shl(12), m);
  119. /// ```
  120. fn signed_shl(self, n: u32) -> Self;
  121. /// Shifts the bits to the right by a specified amount amount, `n`, copying
  122. /// the "sign bit" in the most significant bits even for unsigned types.
  123. ///
  124. /// This is bitwise equivalent to signed `Shr`.
  125. ///
  126. /// # Examples
  127. ///
  128. /// ```
  129. /// use num_traits::PrimInt;
  130. ///
  131. /// let n = 0xFEDCBA9876543210u64;
  132. /// let m = 0xFFFFEDCBA9876543u64;
  133. ///
  134. /// assert_eq!(n.signed_shr(12), m);
  135. /// ```
  136. fn signed_shr(self, n: u32) -> Self;
  137. /// Shifts the bits to the left by a specified amount amount, `n`, filling
  138. /// zeros in the least significant bits.
  139. ///
  140. /// This is bitwise equivalent to unsigned `Shl`.
  141. ///
  142. /// # Examples
  143. ///
  144. /// ```
  145. /// use num_traits::PrimInt;
  146. ///
  147. /// let n = 0x0123456789ABCDEFi64;
  148. /// let m = 0x3456789ABCDEF000i64;
  149. ///
  150. /// assert_eq!(n.unsigned_shl(12), m);
  151. /// ```
  152. fn unsigned_shl(self, n: u32) -> Self;
  153. /// Shifts the bits to the right by a specified amount amount, `n`, filling
  154. /// zeros in the most significant bits.
  155. ///
  156. /// This is bitwise equivalent to unsigned `Shr`.
  157. ///
  158. /// # Examples
  159. ///
  160. /// ```
  161. /// use num_traits::PrimInt;
  162. ///
  163. /// let n = -8i8; // 0b11111000
  164. /// let m = 62i8; // 0b00111110
  165. ///
  166. /// assert_eq!(n.unsigned_shr(2), m);
  167. /// ```
  168. fn unsigned_shr(self, n: u32) -> Self;
  169. /// Reverses the byte order of the integer.
  170. ///
  171. /// # Examples
  172. ///
  173. /// ```
  174. /// use num_traits::PrimInt;
  175. ///
  176. /// let n = 0x0123456789ABCDEFu64;
  177. /// let m = 0xEFCDAB8967452301u64;
  178. ///
  179. /// assert_eq!(n.swap_bytes(), m);
  180. /// ```
  181. fn swap_bytes(self) -> Self;
  182. /// Convert an integer from big endian to the target's endianness.
  183. ///
  184. /// On big endian this is a no-op. On little endian the bytes are swapped.
  185. ///
  186. /// # Examples
  187. ///
  188. /// ```
  189. /// use num_traits::PrimInt;
  190. ///
  191. /// let n = 0x0123456789ABCDEFu64;
  192. ///
  193. /// if cfg!(target_endian = "big") {
  194. /// assert_eq!(u64::from_be(n), n)
  195. /// } else {
  196. /// assert_eq!(u64::from_be(n), n.swap_bytes())
  197. /// }
  198. /// ```
  199. fn from_be(x: Self) -> Self;
  200. /// Convert an integer from little endian to the target's endianness.
  201. ///
  202. /// On little endian this is a no-op. On big endian the bytes are swapped.
  203. ///
  204. /// # Examples
  205. ///
  206. /// ```
  207. /// use num_traits::PrimInt;
  208. ///
  209. /// let n = 0x0123456789ABCDEFu64;
  210. ///
  211. /// if cfg!(target_endian = "little") {
  212. /// assert_eq!(u64::from_le(n), n)
  213. /// } else {
  214. /// assert_eq!(u64::from_le(n), n.swap_bytes())
  215. /// }
  216. /// ```
  217. fn from_le(x: Self) -> Self;
  218. /// Convert `self` to big endian from the target's endianness.
  219. ///
  220. /// On big endian this is a no-op. On little endian the bytes are swapped.
  221. ///
  222. /// # Examples
  223. ///
  224. /// ```
  225. /// use num_traits::PrimInt;
  226. ///
  227. /// let n = 0x0123456789ABCDEFu64;
  228. ///
  229. /// if cfg!(target_endian = "big") {
  230. /// assert_eq!(n.to_be(), n)
  231. /// } else {
  232. /// assert_eq!(n.to_be(), n.swap_bytes())
  233. /// }
  234. /// ```
  235. fn to_be(self) -> Self;
  236. /// Convert `self` to little endian from the target's endianness.
  237. ///
  238. /// On little endian this is a no-op. On big endian the bytes are swapped.
  239. ///
  240. /// # Examples
  241. ///
  242. /// ```
  243. /// use num_traits::PrimInt;
  244. ///
  245. /// let n = 0x0123456789ABCDEFu64;
  246. ///
  247. /// if cfg!(target_endian = "little") {
  248. /// assert_eq!(n.to_le(), n)
  249. /// } else {
  250. /// assert_eq!(n.to_le(), n.swap_bytes())
  251. /// }
  252. /// ```
  253. fn to_le(self) -> Self;
  254. /// Raises self to the power of `exp`, using exponentiation by squaring.
  255. ///
  256. /// # Examples
  257. ///
  258. /// ```
  259. /// use num_traits::PrimInt;
  260. ///
  261. /// assert_eq!(2i32.pow(4), 16);
  262. /// ```
  263. fn pow(self, exp: u32) -> Self;
  264. }
  265. macro_rules! prim_int_impl {
  266. ($T:ty, $S:ty, $U:ty) => {
  267. impl PrimInt for $T {
  268. #[inline]
  269. fn count_ones(self) -> u32 {
  270. <$T>::count_ones(self)
  271. }
  272. #[inline]
  273. fn count_zeros(self) -> u32 {
  274. <$T>::count_zeros(self)
  275. }
  276. #[inline]
  277. fn leading_zeros(self) -> u32 {
  278. <$T>::leading_zeros(self)
  279. }
  280. #[inline]
  281. fn trailing_zeros(self) -> u32 {
  282. <$T>::trailing_zeros(self)
  283. }
  284. #[inline]
  285. fn rotate_left(self, n: u32) -> Self {
  286. <$T>::rotate_left(self, n)
  287. }
  288. #[inline]
  289. fn rotate_right(self, n: u32) -> Self {
  290. <$T>::rotate_right(self, n)
  291. }
  292. #[inline]
  293. fn signed_shl(self, n: u32) -> Self {
  294. ((self as $S) << n) as $T
  295. }
  296. #[inline]
  297. fn signed_shr(self, n: u32) -> Self {
  298. ((self as $S) >> n) as $T
  299. }
  300. #[inline]
  301. fn unsigned_shl(self, n: u32) -> Self {
  302. ((self as $U) << n) as $T
  303. }
  304. #[inline]
  305. fn unsigned_shr(self, n: u32) -> Self {
  306. ((self as $U) >> n) as $T
  307. }
  308. #[inline]
  309. fn swap_bytes(self) -> Self {
  310. <$T>::swap_bytes(self)
  311. }
  312. #[inline]
  313. fn from_be(x: Self) -> Self {
  314. <$T>::from_be(x)
  315. }
  316. #[inline]
  317. fn from_le(x: Self) -> Self {
  318. <$T>::from_le(x)
  319. }
  320. #[inline]
  321. fn to_be(self) -> Self {
  322. <$T>::to_be(self)
  323. }
  324. #[inline]
  325. fn to_le(self) -> Self {
  326. <$T>::to_le(self)
  327. }
  328. #[inline]
  329. fn pow(self, exp: u32) -> Self {
  330. <$T>::pow(self, exp)
  331. }
  332. }
  333. };
  334. }
  335. // prim_int_impl!(type, signed, unsigned);
  336. prim_int_impl!(u8, i8, u8);
  337. prim_int_impl!(u16, i16, u16);
  338. prim_int_impl!(u32, i32, u32);
  339. prim_int_impl!(u64, i64, u64);
  340. #[cfg(has_i128)]
  341. prim_int_impl!(u128, i128, u128);
  342. prim_int_impl!(usize, isize, usize);
  343. prim_int_impl!(i8, i8, u8);
  344. prim_int_impl!(i16, i16, u16);
  345. prim_int_impl!(i32, i32, u32);
  346. prim_int_impl!(i64, i64, u64);
  347. #[cfg(has_i128)]
  348. prim_int_impl!(i128, i128, u128);
  349. prim_int_impl!(isize, isize, usize);