rust_decimal/decimal.rs
1use crate::constants::{
2 MAX_I128_REPR, MAX_SCALE_U32, POWERS_10, SCALE_MASK, SCALE_SHIFT, SIGN_MASK, SIGN_SHIFT, U32_MASK, U8_MASK,
3 UNSIGN_MASK,
4};
5use crate::ops;
6use crate::Error;
7use core::{
8 cmp::{Ordering::Equal, *},
9 fmt,
10 hash::{Hash, Hasher},
11 iter::{Product, Sum},
12 ops::{Add, AddAssign, Div, DivAssign, Mul, MulAssign, Neg, Rem, RemAssign, Sub, SubAssign},
13 str::FromStr,
14};
15
16// Diesel configuration
17#[cfg(feature = "diesel")]
18use diesel::{deserialize::FromSqlRow, expression::AsExpression, sql_types::Numeric};
19
20#[allow(unused_imports)] // It's not actually dead code below, but the compiler thinks it is.
21#[cfg(not(feature = "std"))]
22use num_traits::float::FloatCore;
23use num_traits::{FromPrimitive, Num, One, Signed, ToPrimitive, Zero};
24#[cfg(feature = "rkyv")]
25use rkyv::{Archive, Deserialize, Serialize};
26#[cfg(all(target_arch = "wasm32", feature = "wasm"))]
27use wasm_bindgen::prelude::wasm_bindgen;
28
29/// The smallest value that can be represented by this decimal type.
30const MIN: Decimal = Decimal {
31 flags: 2_147_483_648,
32 lo: 4_294_967_295,
33 mid: 4_294_967_295,
34 hi: 4_294_967_295,
35};
36
37/// The largest value that can be represented by this decimal type.
38const MAX: Decimal = Decimal {
39 flags: 0,
40 lo: 4_294_967_295,
41 mid: 4_294_967_295,
42 hi: 4_294_967_295,
43};
44
45const ZERO: Decimal = Decimal {
46 flags: 0,
47 lo: 0,
48 mid: 0,
49 hi: 0,
50};
51const ONE: Decimal = Decimal {
52 flags: 0,
53 lo: 1,
54 mid: 0,
55 hi: 0,
56};
57const TWO: Decimal = Decimal {
58 flags: 0,
59 lo: 2,
60 mid: 0,
61 hi: 0,
62};
63const TEN: Decimal = Decimal {
64 flags: 0,
65 lo: 10,
66 mid: 0,
67 hi: 0,
68};
69const ONE_HUNDRED: Decimal = Decimal {
70 flags: 0,
71 lo: 100,
72 mid: 0,
73 hi: 0,
74};
75const ONE_THOUSAND: Decimal = Decimal {
76 flags: 0,
77 lo: 1000,
78 mid: 0,
79 hi: 0,
80};
81const NEGATIVE_ONE: Decimal = Decimal {
82 flags: 2147483648,
83 lo: 1,
84 mid: 0,
85 hi: 0,
86};
87
88/// `UnpackedDecimal` contains unpacked representation of `Decimal` where each component
89/// of decimal-format stored in it's own field
90#[derive(Clone, Copy, Debug, PartialEq)]
91pub struct UnpackedDecimal {
92 pub negative: bool,
93 pub scale: u32,
94 pub hi: u32,
95 pub mid: u32,
96 pub lo: u32,
97}
98
99/// `Decimal` represents a 128 bit representation of a fixed-precision decimal number.
100/// The finite set of values of type `Decimal` are of the form m / 10<sup>e</sup>,
101/// where m is an integer such that -2<sup>96</sup> < m < 2<sup>96</sup>, and e is an integer
102/// between 0 and 28 inclusive.
103#[derive(Clone, Copy)]
104#[cfg_attr(feature = "diesel", derive(FromSqlRow, AsExpression), diesel(sql_type = Numeric))]
105#[cfg_attr(feature = "c-repr", repr(C))]
106#[cfg_attr(feature = "align16", repr(align(16)))]
107#[cfg_attr(
108 feature = "borsh",
109 derive(borsh::BorshDeserialize, borsh::BorshSerialize, borsh::BorshSchema)
110)]
111#[cfg_attr(feature = "bytemuck", derive(bytemuck_derive::Pod, bytemuck_derive::Zeroable))]
112#[cfg_attr(
113 feature = "rkyv",
114 derive(Archive, Deserialize, Serialize),
115 archive(compare(PartialEq)),
116 archive_attr(derive(Clone, Copy, Debug))
117)]
118#[cfg_attr(feature = "rkyv-safe", archive(check_bytes))]
119#[cfg_attr(all(target_arch = "wasm32", feature = "wasm"), wasm_bindgen)]
120pub struct Decimal {
121 // Bits 0-15: unused
122 // Bits 16-23: Contains "e", a value between 0-28 that indicates the scale
123 // Bits 24-30: unused
124 // Bit 31: the sign of the Decimal value, 0 meaning positive and 1 meaning negative.
125 flags: u32,
126 // The lo, mid, hi, and flags fields contain the representation of the
127 // Decimal value as a 96-bit integer.
128 hi: u32,
129 lo: u32,
130 mid: u32,
131}
132
133#[cfg(feature = "ndarray")]
134impl ndarray::ScalarOperand for Decimal {}
135
136/// `RoundingStrategy` represents the different rounding strategies that can be used by
137/// `round_dp_with_strategy`.
138#[derive(Clone, Copy, PartialEq, Eq, Debug)]
139pub enum RoundingStrategy {
140 /// When a number is halfway between two others, it is rounded toward the nearest even number.
141 /// Also known as "Bankers Rounding".
142 /// e.g.
143 /// 6.5 -> 6, 7.5 -> 8
144 MidpointNearestEven,
145 /// When a number is halfway between two others, it is rounded toward the nearest number that
146 /// is away from zero. e.g. 6.4 -> 6, 6.5 -> 7, -6.5 -> -7
147 MidpointAwayFromZero,
148 /// When a number is halfway between two others, it is rounded toward the nearest number that
149 /// is toward zero. e.g. 6.4 -> 6, 6.5 -> 6, -6.5 -> -6
150 MidpointTowardZero,
151 /// The number is always rounded toward zero. e.g. -6.8 -> -6, 6.8 -> 6
152 ToZero,
153 /// The number is always rounded away from zero. e.g. -6.8 -> -7, 6.8 -> 7
154 AwayFromZero,
155 /// The number is always rounded towards negative infinity. e.g. 6.8 -> 6, -6.8 -> -7
156 ToNegativeInfinity,
157 /// The number is always rounded towards positive infinity. e.g. 6.8 -> 7, -6.8 -> -6
158 ToPositiveInfinity,
159
160 /// When a number is halfway between two others, it is rounded toward the nearest even number.
161 /// e.g.
162 /// 6.5 -> 6, 7.5 -> 8
163 #[deprecated(since = "1.11.0", note = "Please use RoundingStrategy::MidpointNearestEven instead")]
164 BankersRounding,
165 /// Rounds up if the value >= 5, otherwise rounds down, e.g. 6.5 -> 7
166 #[deprecated(since = "1.11.0", note = "Please use RoundingStrategy::MidpointAwayFromZero instead")]
167 RoundHalfUp,
168 /// Rounds down if the value =< 5, otherwise rounds up, e.g. 6.5 -> 6, 6.51 -> 7 1.4999999 -> 1
169 #[deprecated(since = "1.11.0", note = "Please use RoundingStrategy::MidpointTowardZero instead")]
170 RoundHalfDown,
171 /// Always round down.
172 #[deprecated(since = "1.11.0", note = "Please use RoundingStrategy::ToZero instead")]
173 RoundDown,
174 /// Always round up.
175 #[deprecated(since = "1.11.0", note = "Please use RoundingStrategy::AwayFromZero instead")]
176 RoundUp,
177}
178
179#[allow(dead_code)]
180impl Decimal {
181 /// The smallest value that can be represented by this decimal type.
182 ///
183 /// # Examples
184 ///
185 /// Basic usage:
186 /// ```
187 /// # use rust_decimal::Decimal;
188 /// # use rust_decimal_macros::dec;
189 /// assert_eq!(Decimal::MIN, dec!(-79_228_162_514_264_337_593_543_950_335));
190 /// ```
191 pub const MIN: Decimal = MIN;
192 /// The largest value that can be represented by this decimal type.
193 ///
194 /// # Examples
195 ///
196 /// Basic usage:
197 /// ```
198 /// # use rust_decimal::Decimal;
199 /// # use rust_decimal_macros::dec;
200 /// assert_eq!(Decimal::MAX, dec!(79_228_162_514_264_337_593_543_950_335));
201 /// ```
202 pub const MAX: Decimal = MAX;
203 /// A constant representing 0.
204 ///
205 /// # Examples
206 ///
207 /// Basic usage:
208 /// ```
209 /// # use rust_decimal::Decimal;
210 /// # use rust_decimal_macros::dec;
211 /// assert_eq!(Decimal::ZERO, dec!(0));
212 /// ```
213 pub const ZERO: Decimal = ZERO;
214 /// A constant representing 1.
215 ///
216 /// # Examples
217 ///
218 /// Basic usage:
219 /// ```
220 /// # use rust_decimal::Decimal;
221 /// # use rust_decimal_macros::dec;
222 /// assert_eq!(Decimal::ONE, dec!(1));
223 /// ```
224 pub const ONE: Decimal = ONE;
225 /// A constant representing -1.
226 ///
227 /// # Examples
228 ///
229 /// Basic usage:
230 /// ```
231 /// # use rust_decimal::Decimal;
232 /// # use rust_decimal_macros::dec;
233 /// assert_eq!(Decimal::NEGATIVE_ONE, dec!(-1));
234 /// ```
235 pub const NEGATIVE_ONE: Decimal = NEGATIVE_ONE;
236 /// A constant representing 2.
237 ///
238 /// # Examples
239 ///
240 /// Basic usage:
241 /// ```
242 /// # use rust_decimal::Decimal;
243 /// # use rust_decimal_macros::dec;
244 /// assert_eq!(Decimal::TWO, dec!(2));
245 /// ```
246 pub const TWO: Decimal = TWO;
247 /// A constant representing 10.
248 ///
249 /// # Examples
250 ///
251 /// Basic usage:
252 /// ```
253 /// # use rust_decimal::Decimal;
254 /// # use rust_decimal_macros::dec;
255 /// assert_eq!(Decimal::TEN, dec!(10));
256 /// ```
257 pub const TEN: Decimal = TEN;
258 /// A constant representing 100.
259 ///
260 /// # Examples
261 ///
262 /// Basic usage:
263 /// ```
264 /// # use rust_decimal::Decimal;
265 /// # use rust_decimal_macros::dec;
266 /// assert_eq!(Decimal::ONE_HUNDRED, dec!(100));
267 /// ```
268 pub const ONE_HUNDRED: Decimal = ONE_HUNDRED;
269 /// A constant representing 1000.
270 ///
271 /// # Examples
272 ///
273 /// Basic usage:
274 /// ```
275 /// # use rust_decimal::Decimal;
276 /// # use rust_decimal_macros::dec;
277 /// assert_eq!(Decimal::ONE_THOUSAND, dec!(1000));
278 /// ```
279 pub const ONE_THOUSAND: Decimal = ONE_THOUSAND;
280 /// The maximum supported scale value.
281 ///
282 /// Some operations, such as [`Self::rescale`] may accept larger scale values, but these
283 /// operations will result in a final value with a scale no larger than this.
284 ///
285 /// Note that the maximum scale is _not_ the same as the maximum possible numeric precision in
286 /// base-10.
287 pub const MAX_SCALE: u32 = MAX_SCALE_U32;
288
289 /// A constant representing π as 3.1415926535897932384626433833
290 ///
291 /// # Examples
292 ///
293 /// Basic usage:
294 /// ```
295 /// # use rust_decimal::Decimal;
296 /// # use rust_decimal_macros::dec;
297 /// assert_eq!(Decimal::PI, dec!(3.1415926535897932384626433833));
298 /// ```
299 #[cfg(feature = "maths")]
300 pub const PI: Decimal = Decimal {
301 flags: 1835008,
302 lo: 1102470953,
303 mid: 185874565,
304 hi: 1703060790,
305 };
306 /// A constant representing π/2 as 1.5707963267948966192313216916
307 ///
308 /// # Examples
309 ///
310 /// Basic usage:
311 /// ```
312 /// # use rust_decimal::Decimal;
313 /// # use rust_decimal_macros::dec;
314 /// assert_eq!(Decimal::HALF_PI, dec!(1.5707963267948966192313216916));
315 /// ```
316 #[cfg(feature = "maths")]
317 pub const HALF_PI: Decimal = Decimal {
318 flags: 1835008,
319 lo: 2698719124,
320 mid: 92937282,
321 hi: 851530395,
322 };
323 /// A constant representing π/4 as 0.7853981633974483096156608458
324 ///
325 /// # Examples
326 ///
327 /// Basic usage:
328 /// ```
329 /// # use rust_decimal::Decimal;
330 /// # use rust_decimal_macros::dec;
331 /// assert_eq!(Decimal::QUARTER_PI, dec!(0.7853981633974483096156608458));
332 /// ```
333 #[cfg(feature = "maths")]
334 pub const QUARTER_PI: Decimal = Decimal {
335 flags: 1835008,
336 lo: 1349359562,
337 mid: 2193952289,
338 hi: 425765197,
339 };
340 /// A constant representing 2π as 6.2831853071795864769252867666
341 ///
342 /// # Examples
343 ///
344 /// Basic usage:
345 /// ```
346 /// # use rust_decimal::Decimal;
347 /// # use rust_decimal_macros::dec;
348 /// assert_eq!(Decimal::TWO_PI, dec!(6.2831853071795864769252867666));
349 /// ```
350 #[cfg(feature = "maths")]
351 pub const TWO_PI: Decimal = Decimal {
352 flags: 1835008,
353 lo: 2204941906,
354 mid: 371749130,
355 hi: 3406121580,
356 };
357 /// A constant representing Euler's number (e) as 2.7182818284590452353602874714
358 ///
359 /// # Examples
360 ///
361 /// Basic usage:
362 /// ```
363 /// # use rust_decimal::Decimal;
364 /// # use rust_decimal_macros::dec;
365 /// assert_eq!(Decimal::E, dec!(2.7182818284590452353602874714));
366 /// ```
367 #[cfg(feature = "maths")]
368 pub const E: Decimal = Decimal {
369 flags: 1835008,
370 lo: 2239425882,
371 mid: 3958169141,
372 hi: 1473583531,
373 };
374 /// A constant representing the inverse of Euler's number (1/e) as 0.3678794411714423215955237702
375 ///
376 /// # Examples
377 ///
378 /// Basic usage:
379 /// ```
380 /// # use rust_decimal::Decimal;
381 /// # use rust_decimal_macros::dec;
382 /// assert_eq!(Decimal::E_INVERSE, dec!(0.3678794411714423215955237702));
383 /// ```
384 #[cfg(feature = "maths")]
385 pub const E_INVERSE: Decimal = Decimal {
386 flags: 1835008,
387 lo: 2384059206,
388 mid: 2857938002,
389 hi: 199427844,
390 };
391
392 /// Returns a `Decimal` with a 64 bit `m` representation and corresponding `e` scale.
393 ///
394 /// # Arguments
395 ///
396 /// * `num` - An i64 that represents the `m` portion of the decimal number
397 /// * `scale` - A u32 representing the `e` portion of the decimal number.
398 ///
399 /// # Panics
400 ///
401 /// This function panics if `scale` is > [`Self::MAX_SCALE`].
402 ///
403 /// # Example
404 ///
405 /// ```
406 /// # use rust_decimal::Decimal;
407 /// #
408 /// let pi = Decimal::new(3141, 3);
409 /// assert_eq!(pi.to_string(), "3.141");
410 /// ```
411 #[must_use]
412 pub fn new(num: i64, scale: u32) -> Decimal {
413 match Self::try_new(num, scale) {
414 Err(e) => panic!("{}", e),
415 Ok(d) => d,
416 }
417 }
418
419 /// Checked version of [`Self::new`]. Will return an error instead of panicking at run-time.
420 ///
421 /// # Example
422 ///
423 /// ```rust
424 /// # use rust_decimal::Decimal;
425 /// #
426 /// let max = Decimal::try_new(i64::MAX, u32::MAX);
427 /// assert!(max.is_err());
428 /// ```
429 pub const fn try_new(num: i64, scale: u32) -> crate::Result<Decimal> {
430 if scale > Self::MAX_SCALE {
431 return Err(Error::ScaleExceedsMaximumPrecision(scale));
432 }
433 let flags: u32 = scale << SCALE_SHIFT;
434 if num < 0 {
435 let pos_num = num.wrapping_neg() as u64;
436 return Ok(Decimal {
437 flags: flags | SIGN_MASK,
438 hi: 0,
439 lo: (pos_num & U32_MASK) as u32,
440 mid: ((pos_num >> 32) & U32_MASK) as u32,
441 });
442 }
443 Ok(Decimal {
444 flags,
445 hi: 0,
446 lo: (num as u64 & U32_MASK) as u32,
447 mid: ((num as u64 >> 32) & U32_MASK) as u32,
448 })
449 }
450
451 /// Creates a `Decimal` using a 128 bit signed `m` representation and corresponding `e` scale.
452 ///
453 /// # Arguments
454 ///
455 /// * `num` - An i128 that represents the `m` portion of the decimal number
456 /// * `scale` - A u32 representing the `e` portion of the decimal number.
457 ///
458 /// # Panics
459 ///
460 /// This function panics if `scale` is > [`Self::MAX_SCALE`] or if `num` exceeds the maximum
461 /// supported 96 bits.
462 ///
463 /// # Example
464 ///
465 /// ```rust
466 /// # use rust_decimal::Decimal;
467 /// #
468 /// let pi = Decimal::from_i128_with_scale(3141i128, 3);
469 /// assert_eq!(pi.to_string(), "3.141");
470 /// ```
471 #[must_use]
472 pub fn from_i128_with_scale(num: i128, scale: u32) -> Decimal {
473 match Self::try_from_i128_with_scale(num, scale) {
474 Ok(d) => d,
475 Err(e) => panic!("{}", e),
476 }
477 }
478
479 /// Checked version of `Decimal::from_i128_with_scale`. Will return `Err` instead
480 /// of panicking at run-time.
481 ///
482 /// # Example
483 ///
484 /// ```rust
485 /// # use rust_decimal::Decimal;
486 /// #
487 /// let max = Decimal::try_from_i128_with_scale(i128::MAX, u32::MAX);
488 /// assert!(max.is_err());
489 /// ```
490 pub const fn try_from_i128_with_scale(num: i128, scale: u32) -> crate::Result<Decimal> {
491 if scale > Self::MAX_SCALE {
492 Err(Error::ScaleExceedsMaximumPrecision(scale))
493 } else if num > MAX_I128_REPR {
494 Err(Error::ExceedsMaximumPossibleValue)
495 } else if num < -MAX_I128_REPR {
496 Err(Error::LessThanMinimumPossibleValue)
497 } else {
498 Ok(Self::from_i128_with_scale_unchecked(num, scale))
499 }
500 }
501
502 #[inline]
503 pub(crate) const fn from_i128_with_scale_unchecked(num: i128, scale: u32) -> Decimal {
504 let flags = flags(num < 0, scale);
505 let num = num.unsigned_abs();
506 Decimal {
507 flags,
508 lo: (num as u64 & U32_MASK) as u32,
509 mid: ((num as u64 >> 32) & U32_MASK) as u32,
510 hi: ((num >> 64) as u64 & U32_MASK) as u32,
511 }
512 }
513
514 /// Returns a `Decimal` using the instances constituent parts.
515 ///
516 /// # Arguments
517 ///
518 /// * `lo` - The low 32 bits of a 96-bit integer.
519 /// * `mid` - The middle 32 bits of a 96-bit integer.
520 /// * `hi` - The high 32 bits of a 96-bit integer.
521 /// * `negative` - `true` to indicate a negative number.
522 /// * `scale` - A power of 10 ranging from 0 to [`Self::MAX_SCALE`].
523 ///
524 /// # Example
525 ///
526 /// ```
527 /// # use rust_decimal::Decimal;
528 /// #
529 /// let pi = Decimal::from_parts(1102470952, 185874565, 1703060790, false, 28);
530 /// assert_eq!(pi.to_string(), "3.1415926535897932384626433832");
531 /// ```
532 #[inline]
533 #[must_use]
534 pub const fn from_parts(lo: u32, mid: u32, hi: u32, negative: bool, scale: u32) -> Decimal {
535 assert!(scale <= Self::MAX_SCALE, "Scale exceeds maximum supported scale");
536 Decimal {
537 lo,
538 mid,
539 hi,
540 flags: flags(
541 if lo == 0 && mid == 0 && hi == 0 {
542 false
543 } else {
544 negative
545 },
546 scale,
547 ),
548 }
549 }
550
551 #[must_use]
552 pub(crate) const fn from_parts_raw(lo: u32, mid: u32, hi: u32, flags: u32) -> Decimal {
553 if lo == 0 && mid == 0 && hi == 0 {
554 Decimal {
555 lo,
556 mid,
557 hi,
558 flags: flags & SCALE_MASK,
559 }
560 } else {
561 Decimal { flags, hi, lo, mid }
562 }
563 }
564
565 /// Returns a `Result` which if successful contains the `Decimal` constitution of
566 /// the scientific notation provided by `value`.
567 ///
568 /// # Arguments
569 ///
570 /// * `value` - The scientific notation of the `Decimal`.
571 ///
572 /// # Example
573 ///
574 /// ```
575 /// # use rust_decimal::Decimal;
576 /// #
577 /// # fn main() -> Result<(), rust_decimal::Error> {
578 /// let value = Decimal::from_scientific("9.7e-7")?;
579 /// assert_eq!(value.to_string(), "0.00000097");
580 /// # Ok(())
581 /// # }
582 /// ```
583 pub fn from_scientific(value: &str) -> Result<Decimal, Error> {
584 const ERROR_MESSAGE: &str = "Failed to parse";
585
586 let mut split = value.splitn(2, ['e', 'E']);
587
588 let base = split.next().ok_or_else(|| Error::from(ERROR_MESSAGE))?;
589 let exp = split.next().ok_or_else(|| Error::from(ERROR_MESSAGE))?;
590
591 let mut ret = Decimal::from_str(base)?;
592 let current_scale = ret.scale();
593
594 if let Some(stripped) = exp.strip_prefix('-') {
595 let exp: u32 = stripped.parse().map_err(|_| Error::from(ERROR_MESSAGE))?;
596 if exp > Self::MAX_SCALE {
597 return Err(Error::ScaleExceedsMaximumPrecision(exp));
598 }
599 ret.set_scale(current_scale + exp)?;
600 } else {
601 let exp: u32 = exp.parse().map_err(|_| Error::from(ERROR_MESSAGE))?;
602 if exp <= current_scale {
603 ret.set_scale(current_scale - exp)?;
604 } else if exp > 0 {
605 use crate::constants::BIG_POWERS_10;
606
607 // This is a case whereby the mantissa needs to be larger to be correctly
608 // represented within the decimal type. A good example is 1.2E10. At this point,
609 // we've parsed 1.2 as the base and 10 as the exponent. To represent this within a
610 // Decimal type we effectively store the mantissa as 12,000,000,000 and scale as
611 // zero.
612 if exp > Self::MAX_SCALE {
613 return Err(Error::ScaleExceedsMaximumPrecision(exp));
614 }
615 let mut exp = exp as usize;
616 // Max two iterations. If exp is 1 then it needs to index position 0 of the array.
617 while exp > 0 {
618 let pow;
619 if exp >= BIG_POWERS_10.len() {
620 pow = BIG_POWERS_10[BIG_POWERS_10.len() - 1];
621 exp -= BIG_POWERS_10.len();
622 } else {
623 pow = BIG_POWERS_10[exp - 1];
624 exp = 0;
625 }
626
627 let pow = Decimal {
628 flags: 0,
629 lo: pow as u32,
630 mid: (pow >> 32) as u32,
631 hi: 0,
632 };
633 match ret.checked_mul(pow) {
634 Some(r) => ret = r,
635 None => return Err(Error::ExceedsMaximumPossibleValue),
636 };
637 }
638 ret.normalize_assign();
639 }
640 }
641 Ok(ret)
642 }
643
644 /// Returns a `Result` which if successful contains the `Decimal` constitution of
645 /// the scientific notation provided by `value`. If the exponent is negative and
646 /// the given base and exponent would exceed [Decimal::MAX_SCALE] then this
647 /// functions attempts to round the base to fit.
648 ///
649 /// # Arguments
650 ///
651 /// * `value` - The scientific notation of the `Decimal`.
652 ///
653 /// # Example
654 ///
655 /// ```
656 /// # use rust_decimal::Decimal;
657 /// # use rust_decimal::Error;
658 /// #
659 /// # fn main() -> Result<(), rust_decimal::Error> {
660 /// let value = Decimal::from_scientific_lossy("2.710505431213761e-20")?;
661 /// assert_eq!(value.to_string(), "0.0000000000000000000271050543");
662 ///
663 /// let value = Decimal::from_scientific_lossy("2.5e-28")?;
664 /// assert_eq!(value.to_string(), "0.0000000000000000000000000003");
665 ///
666 /// let value = Decimal::from_scientific_lossy("-2.5e-28")?;
667 /// assert_eq!(value.to_string(), "-0.0000000000000000000000000003");
668 ///
669 /// let err = Decimal::from_scientific_lossy("2e-29").unwrap_err();
670 /// assert_eq!(err, Error::ScaleExceedsMaximumPrecision(29));
671 /// # Ok(())
672 /// # }
673 /// ```
674 pub fn from_scientific_lossy(value: &str) -> Result<Decimal, Error> {
675 const ERROR_MESSAGE: &str = "Failed to parse";
676
677 let mut split = value.splitn(2, ['e', 'E']);
678
679 let base = split.next().ok_or_else(|| Error::from(ERROR_MESSAGE))?;
680 let exp = split.next().ok_or_else(|| Error::from(ERROR_MESSAGE))?;
681
682 let mut ret = Decimal::from_str(base)?;
683 let current_scale = ret.scale();
684
685 if let Some(stripped) = exp.strip_prefix('-') {
686 let exp: u32 = stripped.parse().map_err(|_| Error::from(ERROR_MESSAGE))?;
687 if exp > Self::MAX_SCALE {
688 return Err(Error::ScaleExceedsMaximumPrecision(exp));
689 }
690 if current_scale + exp > Self::MAX_SCALE {
691 ret.rescale(Self::MAX_SCALE - exp);
692 ret.set_scale(Self::MAX_SCALE)?;
693 } else {
694 ret.set_scale(current_scale + exp)?;
695 }
696 } else {
697 let exp: u32 = exp.parse().map_err(|_| Error::from(ERROR_MESSAGE))?;
698 if exp <= current_scale {
699 ret.set_scale(current_scale - exp)?;
700 } else if exp > 0 {
701 use crate::constants::BIG_POWERS_10;
702
703 // This is a case whereby the mantissa needs to be larger to be correctly
704 // represented within the decimal type. A good example is 1.2E10. At this point,
705 // we've parsed 1.2 as the base and 10 as the exponent. To represent this within a
706 // Decimal type we effectively store the mantissa as 12,000,000,000 and scale as
707 // zero.
708 if exp > Self::MAX_SCALE {
709 return Err(Error::ScaleExceedsMaximumPrecision(exp));
710 }
711 let mut exp = exp as usize;
712 // Max two iterations. If exp is 1 then it needs to index position 0 of the array.
713 while exp > 0 {
714 let pow;
715 if exp >= BIG_POWERS_10.len() {
716 pow = BIG_POWERS_10[BIG_POWERS_10.len() - 1];
717 exp -= BIG_POWERS_10.len();
718 } else {
719 pow = BIG_POWERS_10[exp - 1];
720 exp = 0;
721 }
722
723 let pow = Decimal {
724 flags: 0,
725 lo: pow as u32,
726 mid: (pow >> 32) as u32,
727 hi: 0,
728 };
729 match ret.checked_mul(pow) {
730 Some(r) => ret = r,
731 None => return Err(Error::ExceedsMaximumPossibleValue),
732 };
733 }
734 ret.normalize_assign();
735 }
736 }
737 Ok(ret)
738 }
739
740 /// Converts a string slice in a given base to a decimal.
741 ///
742 /// The string is expected to be an optional + sign followed by digits.
743 /// Digits are a subset of these characters, depending on radix, and will return an error if outside
744 /// the expected range:
745 ///
746 /// * 0-9
747 /// * a-z
748 /// * A-Z
749 ///
750 /// # Examples
751 ///
752 /// Basic usage:
753 ///
754 /// ```
755 /// # use rust_decimal::prelude::*;
756 /// #
757 /// # fn main() -> Result<(), rust_decimal::Error> {
758 /// assert_eq!(Decimal::from_str_radix("A", 16)?.to_string(), "10");
759 /// # Ok(())
760 /// # }
761 /// ```
762 pub fn from_str_radix(str: &str, radix: u32) -> Result<Self, crate::Error> {
763 if radix == 10 {
764 crate::str::parse_str_radix_10(str)
765 } else {
766 crate::str::parse_str_radix_n(str, radix)
767 }
768 }
769
770 /// Parses a string slice into a decimal. If the value underflows and cannot be represented with the
771 /// given scale then this will return an error.
772 ///
773 /// # Examples
774 ///
775 /// Basic usage:
776 ///
777 /// ```
778 /// # use rust_decimal::prelude::*;
779 /// # use rust_decimal::Error;
780 /// #
781 /// # fn main() -> Result<(), rust_decimal::Error> {
782 /// assert_eq!(Decimal::from_str_exact("0.001")?.to_string(), "0.001");
783 /// assert_eq!(Decimal::from_str_exact("0.00000_00000_00000_00000_00000_001")?.to_string(), "0.0000000000000000000000000001");
784 /// assert_eq!(Decimal::from_str_exact("0.00000_00000_00000_00000_00000_0001"), Err(Error::Underflow));
785 /// # Ok(())
786 /// # }
787 /// ```
788 pub fn from_str_exact(str: &str) -> Result<Self, crate::Error> {
789 crate::str::parse_str_radix_10_exact(str)
790 }
791
792 /// Returns a string representation that is similar to [`alloc::string::ToString`] but
793 /// doesn't require a heap allocation.
794 ///
795 /// # Examples
796 ///
797 /// ```
798 /// # use rust_decimal::prelude::*;
799 /// # use rust_decimal::Error;
800 /// #
801 /// # fn main() -> Result<(), rust_decimal::Error> {
802 /// assert_eq!(Decimal::from_str_exact("0.001")?.array_string().as_ref(), "0.001");
803 /// # Ok(())
804 /// # }
805 /// ```
806 pub fn array_string(&self) -> impl AsRef<str> {
807 let (result, _) = crate::str::to_str_internal(self, false, None);
808 result
809 }
810
811 /// Returns the scale of the decimal number, otherwise known as `e`.
812 ///
813 /// # Example
814 ///
815 /// ```
816 /// # use rust_decimal::Decimal;
817 /// #
818 /// let num = Decimal::new(1234, 3);
819 /// assert_eq!(num.scale(), 3u32);
820 /// ```
821 #[inline]
822 #[must_use]
823 pub const fn scale(&self) -> u32 {
824 (self.flags & SCALE_MASK) >> SCALE_SHIFT
825 }
826
827 /// Returns the mantissa of the decimal number.
828 ///
829 /// # Example
830 ///
831 /// ```
832 /// # use rust_decimal::prelude::*;
833 /// # use rust_decimal_macros::dec;
834 ///
835 /// let num = dec!(-1.2345678);
836 /// assert_eq!(num.mantissa(), -12345678i128);
837 /// assert_eq!(num.scale(), 7);
838 /// ```
839 #[must_use]
840 pub const fn mantissa(&self) -> i128 {
841 let raw = (self.lo as i128) | ((self.mid as i128) << 32) | ((self.hi as i128) << 64);
842 if self.is_sign_negative() {
843 -raw
844 } else {
845 raw
846 }
847 }
848
849 /// Returns true if this Decimal number is equivalent to zero.
850 ///
851 /// # Example
852 ///
853 /// ```
854 /// # use rust_decimal::prelude::*;
855 /// #
856 /// let num = Decimal::ZERO;
857 /// assert!(num.is_zero());
858 /// ```
859 #[must_use]
860 pub const fn is_zero(&self) -> bool {
861 self.lo | self.mid | self.hi == 0
862 }
863
864 /// Returns true if this Decimal number has zero fractional part (is equal to an integer)
865 ///
866 /// # Example
867 ///
868 /// ```
869 /// # use rust_decimal::prelude::*;
870 /// # use rust_decimal_macros::dec;
871 /// #
872 /// assert_eq!(dec!(5).is_integer(), true);
873 /// // Trailing zeros are also ignored
874 /// assert_eq!(dec!(5.0000).is_integer(), true);
875 /// // If there is a fractional part then it is not an integer
876 /// assert_eq!(dec!(5.1).is_integer(), false);
877 /// ```
878 #[must_use]
879 pub fn is_integer(&self) -> bool {
880 let scale = self.scale();
881 if scale == 0 || self.is_zero() {
882 return true;
883 }
884
885 // Check if it can be divided by 10^scale without remainder
886 let mut bits = self.mantissa_array3();
887 let mut scale = scale;
888 while scale > 0 {
889 let remainder = if scale > 9 {
890 scale -= 9;
891 ops::array::div_by_u32(&mut bits, POWERS_10[9])
892 } else {
893 let power = POWERS_10[scale as usize];
894 scale = 0;
895 ops::array::div_by_u32(&mut bits, power)
896 };
897 if remainder > 0 {
898 return false;
899 }
900 }
901 true
902 }
903
904 /// An optimized method for changing the sign of a decimal number.
905 ///
906 /// # Arguments
907 ///
908 /// * `positive`: true if the resulting decimal should be positive.
909 ///
910 /// # Example
911 ///
912 /// ```
913 /// # use rust_decimal::Decimal;
914 /// #
915 /// let mut one = Decimal::ONE;
916 /// one.set_sign(false);
917 /// assert_eq!(one.to_string(), "-1");
918 /// ```
919 #[deprecated(since = "1.4.0", note = "please use `set_sign_positive` instead")]
920 pub fn set_sign(&mut self, positive: bool) {
921 self.set_sign_positive(positive);
922 }
923
924 /// An optimized method for changing the sign of a decimal number.
925 ///
926 /// # Arguments
927 ///
928 /// * `positive`: true if the resulting decimal should be positive.
929 ///
930 /// # Example
931 ///
932 /// ```
933 /// # use rust_decimal::Decimal;
934 /// #
935 /// let mut one = Decimal::ONE;
936 /// one.set_sign_positive(false);
937 /// assert_eq!(one.to_string(), "-1");
938 /// ```
939 #[inline(always)]
940 pub fn set_sign_positive(&mut self, positive: bool) {
941 if positive {
942 self.flags &= UNSIGN_MASK;
943 } else {
944 self.flags |= SIGN_MASK;
945 }
946 }
947
948 /// An optimized method for changing the sign of a decimal number.
949 ///
950 /// # Arguments
951 ///
952 /// * `negative`: true if the resulting decimal should be negative.
953 ///
954 /// # Example
955 ///
956 /// ```
957 /// # use rust_decimal::Decimal;
958 /// #
959 /// let mut one = Decimal::ONE;
960 /// one.set_sign_negative(true);
961 /// assert_eq!(one.to_string(), "-1");
962 /// ```
963 #[inline(always)]
964 pub fn set_sign_negative(&mut self, negative: bool) {
965 self.set_sign_positive(!negative);
966 }
967
968 /// An optimized method for changing the scale of a decimal number.
969 ///
970 /// # Arguments
971 ///
972 /// * `scale`: the new scale of the number
973 ///
974 /// # Example
975 ///
976 /// ```
977 /// # use rust_decimal::Decimal;
978 /// #
979 /// # fn main() -> Result<(), rust_decimal::Error> {
980 /// let mut one = Decimal::ONE;
981 /// one.set_scale(5)?;
982 /// assert_eq!(one.to_string(), "0.00001");
983 /// # Ok(())
984 /// # }
985 /// ```
986 pub fn set_scale(&mut self, scale: u32) -> Result<(), Error> {
987 if scale > Self::MAX_SCALE {
988 return Err(Error::ScaleExceedsMaximumPrecision(scale));
989 }
990 self.flags = (scale << SCALE_SHIFT) | (self.flags & SIGN_MASK);
991 Ok(())
992 }
993
994 /// Modifies the `Decimal` towards the desired scale, attempting to do so without changing the
995 /// underlying number itself.
996 ///
997 /// Setting the scale to something less then the current `Decimal`s scale will
998 /// cause the newly created `Decimal` to perform rounding using the `MidpointAwayFromZero` strategy.
999 ///
1000 /// Scales greater than the maximum precision that can be represented by `Decimal` will be
1001 /// automatically rounded to either [`Self::MAX_SCALE`] or the maximum precision that can
1002 /// be represented with the given mantissa.
1003 ///
1004 /// # Arguments
1005 /// * `scale`: The desired scale to use for the new `Decimal` number.
1006 ///
1007 /// # Example
1008 ///
1009 /// ```
1010 /// # use rust_decimal::prelude::*;
1011 /// # use rust_decimal_macros::dec;
1012 ///
1013 /// // Rescaling to a higher scale preserves the value
1014 /// let mut number = dec!(1.123);
1015 /// assert_eq!(number.scale(), 3);
1016 /// number.rescale(6);
1017 /// assert_eq!(number.to_string(), "1.123000");
1018 /// assert_eq!(number.scale(), 6);
1019 ///
1020 /// // Rescaling to a lower scale forces the number to be rounded
1021 /// let mut number = dec!(1.45);
1022 /// assert_eq!(number.scale(), 2);
1023 /// number.rescale(1);
1024 /// assert_eq!(number.to_string(), "1.5");
1025 /// assert_eq!(number.scale(), 1);
1026 ///
1027 /// // This function never fails. Consequently, if a scale is provided that is unable to be
1028 /// // represented using the given mantissa, then the maximum possible scale is used.
1029 /// let mut number = dec!(11.76470588235294);
1030 /// assert_eq!(number.scale(), 14);
1031 /// number.rescale(28);
1032 /// // A scale of 28 cannot be represented given this mantissa, however it was able to represent
1033 /// // a number with a scale of 27
1034 /// assert_eq!(number.to_string(), "11.764705882352940000000000000");
1035 /// assert_eq!(number.scale(), 27);
1036 /// ```
1037 pub fn rescale(&mut self, scale: u32) {
1038 let mut array = [self.lo, self.mid, self.hi];
1039 let mut value_scale = self.scale();
1040 ops::array::rescale_internal(&mut array, &mut value_scale, scale);
1041 self.lo = array[0];
1042 self.mid = array[1];
1043 self.hi = array[2];
1044 self.flags = flags(self.is_sign_negative(), value_scale);
1045 }
1046
1047 /// Returns a serialized version of the decimal number.
1048 /// The resulting byte array will have the following representation:
1049 ///
1050 /// * Bytes 1-4: flags
1051 /// * Bytes 5-8: lo portion of `m`
1052 /// * Bytes 9-12: mid portion of `m`
1053 /// * Bytes 13-16: high portion of `m`
1054 #[must_use]
1055 pub const fn serialize(&self) -> [u8; 16] {
1056 [
1057 (self.flags & U8_MASK) as u8,
1058 ((self.flags >> 8) & U8_MASK) as u8,
1059 ((self.flags >> 16) & U8_MASK) as u8,
1060 ((self.flags >> 24) & U8_MASK) as u8,
1061 (self.lo & U8_MASK) as u8,
1062 ((self.lo >> 8) & U8_MASK) as u8,
1063 ((self.lo >> 16) & U8_MASK) as u8,
1064 ((self.lo >> 24) & U8_MASK) as u8,
1065 (self.mid & U8_MASK) as u8,
1066 ((self.mid >> 8) & U8_MASK) as u8,
1067 ((self.mid >> 16) & U8_MASK) as u8,
1068 ((self.mid >> 24) & U8_MASK) as u8,
1069 (self.hi & U8_MASK) as u8,
1070 ((self.hi >> 8) & U8_MASK) as u8,
1071 ((self.hi >> 16) & U8_MASK) as u8,
1072 ((self.hi >> 24) & U8_MASK) as u8,
1073 ]
1074 }
1075
1076 /// Deserializes the given bytes into a decimal number.
1077 /// The deserialized byte representation must be 16 bytes and adhere to the following convention:
1078 ///
1079 /// * Bytes 1-4: flags
1080 /// * Bytes 5-8: lo portion of `m`
1081 /// * Bytes 9-12: mid portion of `m`
1082 /// * Bytes 13-16: high portion of `m`
1083 #[must_use]
1084 pub fn deserialize(bytes: [u8; 16]) -> Decimal {
1085 // We can bound flags by a bitwise mask to correspond to:
1086 // Bits 0-15: unused
1087 // Bits 16-23: Contains "e", a value between 0-28 that indicates the scale
1088 // Bits 24-30: unused
1089 // Bit 31: the sign of the Decimal value, 0 meaning positive and 1 meaning negative.
1090 let mut raw = Decimal {
1091 flags: ((bytes[0] as u32)
1092 | ((bytes[1] as u32) << 8)
1093 | ((bytes[2] as u32) << 16)
1094 | ((bytes[3] as u32) << 24))
1095 & 0x801F_0000,
1096 lo: (bytes[4] as u32) | ((bytes[5] as u32) << 8) | ((bytes[6] as u32) << 16) | ((bytes[7] as u32) << 24),
1097 mid: (bytes[8] as u32) | ((bytes[9] as u32) << 8) | ((bytes[10] as u32) << 16) | ((bytes[11] as u32) << 24),
1098 hi: (bytes[12] as u32)
1099 | ((bytes[13] as u32) << 8)
1100 | ((bytes[14] as u32) << 16)
1101 | ((bytes[15] as u32) << 24),
1102 };
1103 // Scale must be bound to maximum precision. Only two values can be greater than this
1104 if raw.scale() > Self::MAX_SCALE {
1105 let mut bits = raw.mantissa_array3();
1106 let remainder = match raw.scale() {
1107 29 => ops::array::div_by_power::<1>(&mut bits),
1108 30 => ops::array::div_by_power::<2>(&mut bits),
1109 31 => ops::array::div_by_power::<3>(&mut bits),
1110 _ => 0,
1111 };
1112 if remainder >= 5 {
1113 ops::array::add_one_internal(&mut bits);
1114 }
1115 raw.lo = bits[0];
1116 raw.mid = bits[1];
1117 raw.hi = bits[2];
1118 raw.flags = flags(raw.is_sign_negative(), Self::MAX_SCALE);
1119 }
1120 raw
1121 }
1122
1123 /// Returns `true` if the decimal is negative.
1124 #[deprecated(since = "0.6.3", note = "please use `is_sign_negative` instead")]
1125 #[must_use]
1126 pub fn is_negative(&self) -> bool {
1127 self.is_sign_negative()
1128 }
1129
1130 /// Returns `true` if the decimal is positive.
1131 #[deprecated(since = "0.6.3", note = "please use `is_sign_positive` instead")]
1132 #[must_use]
1133 pub fn is_positive(&self) -> bool {
1134 self.is_sign_positive()
1135 }
1136
1137 /// Returns `true` if the sign bit of the decimal is negative.
1138 ///
1139 /// # Example
1140 /// ```
1141 /// # use rust_decimal::prelude::*;
1142 /// #
1143 /// assert_eq!(true, Decimal::new(-1, 0).is_sign_negative());
1144 /// assert_eq!(false, Decimal::new(1, 0).is_sign_negative());
1145 /// ```
1146 #[inline(always)]
1147 #[must_use]
1148 pub const fn is_sign_negative(&self) -> bool {
1149 self.flags & SIGN_MASK > 0
1150 }
1151
1152 /// Returns `true` if the sign bit of the decimal is positive.
1153 ///
1154 /// # Example
1155 /// ```
1156 /// # use rust_decimal::prelude::*;
1157 /// #
1158 /// assert_eq!(false, Decimal::new(-1, 0).is_sign_positive());
1159 /// assert_eq!(true, Decimal::new(1, 0).is_sign_positive());
1160 /// ```
1161 #[inline(always)]
1162 #[must_use]
1163 pub const fn is_sign_positive(&self) -> bool {
1164 self.flags & SIGN_MASK == 0
1165 }
1166
1167 /// Returns the minimum possible number that `Decimal` can represent.
1168 #[deprecated(since = "1.12.0", note = "Use the associated constant Decimal::MIN")]
1169 #[must_use]
1170 pub const fn min_value() -> Decimal {
1171 MIN
1172 }
1173
1174 /// Returns the maximum possible number that `Decimal` can represent.
1175 #[deprecated(since = "1.12.0", note = "Use the associated constant Decimal::MAX")]
1176 #[must_use]
1177 pub const fn max_value() -> Decimal {
1178 MAX
1179 }
1180
1181 /// Returns a new `Decimal` integral with no fractional portion.
1182 /// This is a true truncation whereby no rounding is performed.
1183 ///
1184 /// # Example
1185 ///
1186 /// ```
1187 /// # use rust_decimal::Decimal;
1188 /// # use rust_decimal_macros::dec;
1189 /// #
1190 /// let pi = dec!(3.141);
1191 /// assert_eq!(pi.trunc(), dec!(3));
1192 ///
1193 /// // Negative numbers are similarly truncated without rounding
1194 /// let neg = dec!(-1.98765);
1195 /// assert_eq!(neg.trunc(), Decimal::NEGATIVE_ONE);
1196 /// ```
1197 #[must_use]
1198 pub fn trunc(&self) -> Decimal {
1199 let mut working = [self.lo, self.mid, self.hi];
1200 let mut working_scale = self.scale();
1201 ops::array::truncate_internal(&mut working, &mut working_scale, 0);
1202 Decimal {
1203 lo: working[0],
1204 mid: working[1],
1205 hi: working[2],
1206 flags: flags(self.is_sign_negative(), working_scale),
1207 }
1208 }
1209
1210 /// Returns a new `Decimal` with the fractional portion delimited by `scale`.
1211 /// This is a true truncation whereby no rounding is performed.
1212 ///
1213 /// # Example
1214 ///
1215 /// ```
1216 /// # use rust_decimal::Decimal;
1217 /// # use rust_decimal_macros::dec;
1218 /// #
1219 /// let pi = dec!(3.141592);
1220 /// assert_eq!(pi.trunc_with_scale(2), dec!(3.14));
1221 ///
1222 /// // Negative numbers are similarly truncated without rounding
1223 /// let neg = dec!(-1.98765);
1224 /// assert_eq!(neg.trunc_with_scale(1), dec!(-1.9));
1225 /// ```
1226 #[must_use]
1227 pub fn trunc_with_scale(&self, scale: u32) -> Decimal {
1228 let mut working = [self.lo, self.mid, self.hi];
1229 let mut working_scale = self.scale();
1230 ops::array::truncate_internal(&mut working, &mut working_scale, scale);
1231 Decimal {
1232 lo: working[0],
1233 mid: working[1],
1234 hi: working[2],
1235 flags: flags(self.is_sign_negative(), working_scale),
1236 }
1237 }
1238
1239 /// Returns a new `Decimal` representing the fractional portion of the number.
1240 ///
1241 /// # Example
1242 ///
1243 /// ```
1244 /// # use rust_decimal::Decimal;
1245 /// #
1246 /// let pi = Decimal::new(3141, 3);
1247 /// let fract = Decimal::new(141, 3);
1248 /// // note that it returns a decimal
1249 /// assert_eq!(pi.fract(), fract);
1250 /// ```
1251 #[must_use]
1252 pub fn fract(&self) -> Decimal {
1253 // This is essentially the original number minus the integral.
1254 // Could possibly be optimized in the future
1255 *self - self.trunc()
1256 }
1257
1258 /// Computes the absolute value of `self`.
1259 ///
1260 /// # Example
1261 ///
1262 /// ```
1263 /// # use rust_decimal::Decimal;
1264 /// #
1265 /// let num = Decimal::new(-3141, 3);
1266 /// assert_eq!(num.abs().to_string(), "3.141");
1267 /// ```
1268 #[must_use]
1269 pub fn abs(&self) -> Decimal {
1270 let mut me = *self;
1271 me.set_sign_positive(true);
1272 me
1273 }
1274
1275 /// Returns the largest integer less than or equal to a number.
1276 ///
1277 /// # Example
1278 ///
1279 /// ```
1280 /// # use rust_decimal::Decimal;
1281 /// #
1282 /// let num = Decimal::new(3641, 3);
1283 /// assert_eq!(num.floor().to_string(), "3");
1284 /// ```
1285 #[must_use]
1286 pub fn floor(&self) -> Decimal {
1287 let scale = self.scale();
1288 if scale == 0 {
1289 // Nothing to do
1290 return *self;
1291 }
1292
1293 // Opportunity for optimization here
1294 let floored = self.trunc();
1295 if self.is_sign_negative() && !self.fract().is_zero() {
1296 floored - ONE
1297 } else {
1298 floored
1299 }
1300 }
1301
1302 /// Returns the smallest integer greater than or equal to a number.
1303 ///
1304 /// # Example
1305 ///
1306 /// ```
1307 /// # use rust_decimal::Decimal;
1308 /// #
1309 /// let num = Decimal::new(3141, 3);
1310 /// assert_eq!(num.ceil().to_string(), "4");
1311 /// let num = Decimal::new(3, 0);
1312 /// assert_eq!(num.ceil().to_string(), "3");
1313 /// ```
1314 #[must_use]
1315 pub fn ceil(&self) -> Decimal {
1316 let scale = self.scale();
1317 if scale == 0 {
1318 // Nothing to do
1319 return *self;
1320 }
1321
1322 // Opportunity for optimization here
1323 if self.is_sign_positive() && !self.fract().is_zero() {
1324 self.trunc() + ONE
1325 } else {
1326 self.trunc()
1327 }
1328 }
1329
1330 /// Returns the maximum of the two numbers.
1331 ///
1332 /// ```
1333 /// # use rust_decimal::Decimal;
1334 /// #
1335 /// let x = Decimal::new(1, 0);
1336 /// let y = Decimal::new(2, 0);
1337 /// assert_eq!(y, x.max(y));
1338 /// ```
1339 #[must_use]
1340 pub fn max(self, other: Decimal) -> Decimal {
1341 if self < other {
1342 other
1343 } else {
1344 self
1345 }
1346 }
1347
1348 /// Returns the minimum of the two numbers.
1349 ///
1350 /// ```
1351 /// # use rust_decimal::Decimal;
1352 /// #
1353 /// let x = Decimal::new(1, 0);
1354 /// let y = Decimal::new(2, 0);
1355 /// assert_eq!(x, x.min(y));
1356 /// ```
1357 #[must_use]
1358 pub fn min(self, other: Decimal) -> Decimal {
1359 if self > other {
1360 other
1361 } else {
1362 self
1363 }
1364 }
1365
1366 /// Strips any trailing zero's from a `Decimal` and converts -0 to 0.
1367 ///
1368 /// # Example
1369 ///
1370 /// ```
1371 /// # use rust_decimal::prelude::*;
1372 /// # fn main() -> Result<(), rust_decimal::Error> {
1373 /// let number = Decimal::from_str("3.100")?;
1374 /// assert_eq!(number.normalize().to_string(), "3.1");
1375 /// # Ok(())
1376 /// # }
1377 /// ```
1378 #[must_use]
1379 pub fn normalize(&self) -> Decimal {
1380 let mut result = *self;
1381 result.normalize_assign();
1382 result
1383 }
1384
1385 /// An in place version of `normalize`. Strips any trailing zero's from a `Decimal` and converts -0 to 0.
1386 ///
1387 /// # Example
1388 ///
1389 /// ```
1390 /// # use rust_decimal::prelude::*;
1391 /// # fn main() -> Result<(), rust_decimal::Error> {
1392 /// let mut number = Decimal::from_str("3.100")?;
1393 /// assert_eq!(number.to_string(), "3.100");
1394 /// number.normalize_assign();
1395 /// assert_eq!(number.to_string(), "3.1");
1396 /// # Ok(())
1397 /// # }
1398 /// ```
1399 pub fn normalize_assign(&mut self) {
1400 if self.is_zero() {
1401 self.flags = 0;
1402 return;
1403 }
1404
1405 let mut scale = self.scale();
1406 if scale == 0 {
1407 return;
1408 }
1409
1410 let mut result = self.mantissa_array3();
1411 let mut working = self.mantissa_array3();
1412 while scale > 0 {
1413 if ops::array::div_by_u32(&mut working, 10) > 0 {
1414 break;
1415 }
1416 scale -= 1;
1417 result.copy_from_slice(&working);
1418 }
1419 self.lo = result[0];
1420 self.mid = result[1];
1421 self.hi = result[2];
1422 self.flags = flags(self.is_sign_negative(), scale);
1423 }
1424
1425 /// Returns a new `Decimal` number with no fractional portion (i.e. an integer).
1426 /// Rounding currently follows "Bankers Rounding" rules. e.g. 6.5 -> 6, 7.5 -> 8
1427 ///
1428 /// # Example
1429 ///
1430 /// ```
1431 /// # use rust_decimal::Decimal;
1432 /// #
1433 /// // Demonstrating bankers rounding...
1434 /// let number_down = Decimal::new(65, 1);
1435 /// let number_up = Decimal::new(75, 1);
1436 /// assert_eq!(number_down.round().to_string(), "6");
1437 /// assert_eq!(number_up.round().to_string(), "8");
1438 /// ```
1439 #[must_use]
1440 pub fn round(&self) -> Decimal {
1441 self.round_dp(0)
1442 }
1443
1444 /// Returns a new `Decimal` number with the specified number of decimal points for fractional
1445 /// portion.
1446 /// Rounding is performed using the provided [`RoundingStrategy`]
1447 ///
1448 /// # Arguments
1449 /// * `dp`: the number of decimal points to round to.
1450 /// * `strategy`: the [`RoundingStrategy`] to use.
1451 ///
1452 /// # Example
1453 ///
1454 /// ```
1455 /// # use rust_decimal::{Decimal, RoundingStrategy};
1456 /// # use rust_decimal_macros::dec;
1457 /// #
1458 /// let tax = dec!(3.4395);
1459 /// assert_eq!(tax.round_dp_with_strategy(2, RoundingStrategy::MidpointAwayFromZero).to_string(), "3.44");
1460 /// ```
1461 #[must_use]
1462 pub fn round_dp_with_strategy(&self, dp: u32, strategy: RoundingStrategy) -> Decimal {
1463 let old_scale = self.scale();
1464
1465 // return early if decimal has a smaller number of fractional places than dp
1466 // e.g. 2.51 rounded to 3 decimal places is 2.51
1467 if old_scale <= dp {
1468 return *self;
1469 }
1470
1471 // Short circuit for zero
1472 if self.is_zero() {
1473 return Decimal {
1474 lo: 0,
1475 mid: 0,
1476 hi: 0,
1477 flags: flags(self.is_sign_negative(), dp),
1478 };
1479 }
1480
1481 let mut value = [self.lo, self.mid, self.hi];
1482 let mut value_scale = self.scale();
1483 let negative = self.is_sign_negative();
1484
1485 value_scale -= dp;
1486
1487 // Rescale to zero so it's easier to work with
1488 while value_scale > 0 {
1489 if value_scale < 10 {
1490 ops::array::div_by_u32(&mut value, POWERS_10[value_scale as usize]);
1491 value_scale = 0;
1492 } else {
1493 ops::array::div_by_u32(&mut value, POWERS_10[9]);
1494 value_scale -= 9;
1495 }
1496 }
1497
1498 // Do some midpoint rounding checks
1499 // We're actually doing two things here.
1500 // 1. Figuring out midpoint rounding when we're right on the boundary. e.g. 2.50000
1501 // 2. Figuring out whether to add one or not e.g. 2.51
1502 // For this, we need to figure out the fractional portion that is additional to
1503 // the rounded number. e.g. for 0.12345 rounding to 2dp we'd want 345.
1504 // We're doing the equivalent of losing precision (e.g. to get 0.12)
1505 // then increasing the precision back up to 0.12000
1506 let mut offset = [self.lo, self.mid, self.hi];
1507 let mut diff = old_scale - dp;
1508
1509 while diff > 0 {
1510 if diff < 10 {
1511 ops::array::div_by_u32(&mut offset, POWERS_10[diff as usize]);
1512 break;
1513 } else {
1514 ops::array::div_by_u32(&mut offset, POWERS_10[9]);
1515 // Only 9 as this array starts with 1
1516 diff -= 9;
1517 }
1518 }
1519
1520 let mut diff = old_scale - dp;
1521
1522 while diff > 0 {
1523 if diff < 10 {
1524 ops::array::mul_by_u32(&mut offset, POWERS_10[diff as usize]);
1525 break;
1526 } else {
1527 ops::array::mul_by_u32(&mut offset, POWERS_10[9]);
1528 // Only 9 as this array starts with 1
1529 diff -= 9;
1530 }
1531 }
1532
1533 let mut decimal_portion = [self.lo, self.mid, self.hi];
1534 ops::array::sub_by_internal(&mut decimal_portion, &offset);
1535
1536 // If the decimal_portion is zero then we round based on the other data
1537 let mut cap = [5, 0, 0];
1538 for _ in 0..(old_scale - dp - 1) {
1539 ops::array::mul_by_u32(&mut cap, 10);
1540 }
1541 let order = ops::array::cmp_internal(&decimal_portion, &cap);
1542
1543 #[allow(deprecated)]
1544 match strategy {
1545 RoundingStrategy::BankersRounding | RoundingStrategy::MidpointNearestEven => {
1546 match order {
1547 Ordering::Equal => {
1548 if (value[0] & 1) == 1 {
1549 ops::array::add_one_internal(&mut value);
1550 }
1551 }
1552 Ordering::Greater => {
1553 // Doesn't matter about the decimal portion
1554 ops::array::add_one_internal(&mut value);
1555 }
1556 _ => {}
1557 }
1558 }
1559 RoundingStrategy::RoundHalfDown | RoundingStrategy::MidpointTowardZero => {
1560 if let Ordering::Greater = order {
1561 ops::array::add_one_internal(&mut value);
1562 }
1563 }
1564 RoundingStrategy::RoundHalfUp | RoundingStrategy::MidpointAwayFromZero => {
1565 // when Ordering::Equal, decimal_portion is 0.5 exactly
1566 // when Ordering::Greater, decimal_portion is > 0.5
1567 match order {
1568 Ordering::Equal => {
1569 ops::array::add_one_internal(&mut value);
1570 }
1571 Ordering::Greater => {
1572 // Doesn't matter about the decimal portion
1573 ops::array::add_one_internal(&mut value);
1574 }
1575 _ => {}
1576 }
1577 }
1578 RoundingStrategy::RoundUp | RoundingStrategy::AwayFromZero => {
1579 if !ops::array::is_all_zero(&decimal_portion) {
1580 ops::array::add_one_internal(&mut value);
1581 }
1582 }
1583 RoundingStrategy::ToPositiveInfinity => {
1584 if !negative && !ops::array::is_all_zero(&decimal_portion) {
1585 ops::array::add_one_internal(&mut value);
1586 }
1587 }
1588 RoundingStrategy::ToNegativeInfinity => {
1589 if negative && !ops::array::is_all_zero(&decimal_portion) {
1590 ops::array::add_one_internal(&mut value);
1591 }
1592 }
1593 RoundingStrategy::RoundDown | RoundingStrategy::ToZero => (),
1594 }
1595
1596 Decimal::from_parts(value[0], value[1], value[2], negative, dp)
1597 }
1598
1599 /// Returns a new `Decimal` number with the specified number of decimal points for fractional portion.
1600 /// Rounding currently follows "Bankers Rounding" rules. e.g. 6.5 -> 6, 7.5 -> 8
1601 ///
1602 /// # Arguments
1603 /// * `dp`: the number of decimal points to round to.
1604 ///
1605 /// # Example
1606 ///
1607 /// ```
1608 /// # use rust_decimal::Decimal;
1609 /// # use rust_decimal_macros::dec;
1610 /// #
1611 /// let pi = dec!(3.1415926535897932384626433832);
1612 /// assert_eq!(pi.round_dp(2).to_string(), "3.14");
1613 /// ```
1614 #[must_use]
1615 pub fn round_dp(&self, dp: u32) -> Decimal {
1616 self.round_dp_with_strategy(dp, RoundingStrategy::MidpointNearestEven)
1617 }
1618
1619 /// Returns `Some(Decimal)` number rounded to the specified number of significant digits. If
1620 /// the resulting number is unable to be represented by the `Decimal` number then `None` will
1621 /// be returned.
1622 /// When the number of significant figures of the `Decimal` being rounded is greater than the requested
1623 /// number of significant digits then rounding will be performed using `MidpointNearestEven` strategy.
1624 ///
1625 /// # Arguments
1626 /// * `digits`: the number of significant digits to round to.
1627 ///
1628 /// # Remarks
1629 /// A significant figure is determined using the following rules:
1630 /// 1. Non-zero digits are always significant.
1631 /// 2. Zeros between non-zero digits are always significant.
1632 /// 3. Leading zeros are never significant.
1633 /// 4. Trailing zeros are only significant if the number contains a decimal point.
1634 ///
1635 /// # Example
1636 ///
1637 /// ```
1638 /// # use rust_decimal::Decimal;
1639 /// # use rust_decimal_macros::dec;
1640 ///
1641 /// let value = dec!(305.459);
1642 /// assert_eq!(value.round_sf(0), Some(dec!(0)));
1643 /// assert_eq!(value.round_sf(1), Some(dec!(300)));
1644 /// assert_eq!(value.round_sf(2), Some(dec!(310)));
1645 /// assert_eq!(value.round_sf(3), Some(dec!(305)));
1646 /// assert_eq!(value.round_sf(4), Some(dec!(305.5)));
1647 /// assert_eq!(value.round_sf(5), Some(dec!(305.46)));
1648 /// assert_eq!(value.round_sf(6), Some(dec!(305.459)));
1649 /// assert_eq!(value.round_sf(7), Some(dec!(305.4590)));
1650 /// assert_eq!(Decimal::MAX.round_sf(1), None);
1651 ///
1652 /// let value = dec!(0.012301);
1653 /// assert_eq!(value.round_sf(3), Some(dec!(0.0123)));
1654 /// ```
1655 #[must_use]
1656 pub fn round_sf(&self, digits: u32) -> Option<Decimal> {
1657 self.round_sf_with_strategy(digits, RoundingStrategy::MidpointNearestEven)
1658 }
1659
1660 /// Returns `Some(Decimal)` number rounded to the specified number of significant digits. If
1661 /// the resulting number is unable to be represented by the `Decimal` number then `None` will
1662 /// be returned.
1663 /// When the number of significant figures of the `Decimal` being rounded is greater than the requested
1664 /// number of significant digits then rounding will be performed using the provided [RoundingStrategy].
1665 ///
1666 /// # Arguments
1667 /// * `digits`: the number of significant digits to round to.
1668 /// * `strategy`: if required, the rounding strategy to use.
1669 ///
1670 /// # Remarks
1671 /// A significant figure is determined using the following rules:
1672 /// 1. Non-zero digits are always significant.
1673 /// 2. Zeros between non-zero digits are always significant.
1674 /// 3. Leading zeros are never significant.
1675 /// 4. Trailing zeros are only significant if the number contains a decimal point.
1676 ///
1677 /// # Example
1678 ///
1679 /// ```
1680 /// # use rust_decimal::{Decimal, RoundingStrategy};
1681 /// # use rust_decimal_macros::dec;
1682 ///
1683 /// let value = dec!(305.459);
1684 /// assert_eq!(value.round_sf_with_strategy(0, RoundingStrategy::ToZero), Some(dec!(0)));
1685 /// assert_eq!(value.round_sf_with_strategy(1, RoundingStrategy::ToZero), Some(dec!(300)));
1686 /// assert_eq!(value.round_sf_with_strategy(2, RoundingStrategy::ToZero), Some(dec!(300)));
1687 /// assert_eq!(value.round_sf_with_strategy(3, RoundingStrategy::ToZero), Some(dec!(305)));
1688 /// assert_eq!(value.round_sf_with_strategy(4, RoundingStrategy::ToZero), Some(dec!(305.4)));
1689 /// assert_eq!(value.round_sf_with_strategy(5, RoundingStrategy::ToZero), Some(dec!(305.45)));
1690 /// assert_eq!(value.round_sf_with_strategy(6, RoundingStrategy::ToZero), Some(dec!(305.459)));
1691 /// assert_eq!(value.round_sf_with_strategy(7, RoundingStrategy::ToZero), Some(dec!(305.4590)));
1692 /// assert_eq!(Decimal::MAX.round_sf_with_strategy(1, RoundingStrategy::ToZero), Some(dec!(70000000000000000000000000000)));
1693 ///
1694 /// let value = dec!(0.012301);
1695 /// assert_eq!(value.round_sf_with_strategy(3, RoundingStrategy::AwayFromZero), Some(dec!(0.0124)));
1696 /// ```
1697 #[must_use]
1698 pub fn round_sf_with_strategy(&self, digits: u32, strategy: RoundingStrategy) -> Option<Decimal> {
1699 if self.is_zero() || digits == 0 {
1700 return Some(Decimal::ZERO);
1701 }
1702
1703 // We start by grabbing the mantissa and figuring out how many significant figures it is
1704 // made up of. We do this by just dividing by 10 and checking remainders - effectively
1705 // we're performing a naive log10.
1706 let mut working = self.mantissa_array3();
1707 let mut mantissa_sf = 0;
1708 while !ops::array::is_all_zero(&working) {
1709 let _remainder = ops::array::div_by_u32(&mut working, 10u32);
1710 mantissa_sf += 1;
1711 if working[2] == 0 && working[1] == 0 && working[0] == 1 {
1712 mantissa_sf += 1;
1713 break;
1714 }
1715 }
1716 let scale = self.scale();
1717
1718 match digits.cmp(&mantissa_sf) {
1719 Ordering::Greater => {
1720 // If we're requesting a higher number of significant figures, we rescale
1721 let mut array = [self.lo, self.mid, self.hi];
1722 let mut value_scale = scale;
1723 ops::array::rescale_internal(&mut array, &mut value_scale, scale + digits - mantissa_sf);
1724 Some(Decimal {
1725 lo: array[0],
1726 mid: array[1],
1727 hi: array[2],
1728 flags: flags(self.is_sign_negative(), value_scale),
1729 })
1730 }
1731 Ordering::Less => {
1732 // We're requesting a lower number of significant digits.
1733 let diff = mantissa_sf - digits;
1734 // If the diff is greater than the scale we're focused on the integral. Otherwise, we can
1735 // just round.
1736 if diff > scale {
1737 use crate::constants::BIG_POWERS_10;
1738 // We need to adjust the integral portion. This also should be rounded, consequently
1739 // we reduce the number down, round it, and then scale back up.
1740 // E.g. If we have 305.459 scaling to a sf of 2 - we first reduce the number
1741 // down to 30.5459, round it to 31 and then scale it back up to 310.
1742 // Likewise, if we have 12301 scaling to a sf of 3 - we first reduce the number
1743 // down to 123.01, round it to 123 and then scale it back up to 12300.
1744 let mut num = *self;
1745 let mut exp = (diff - scale) as usize;
1746 while exp > 0 {
1747 let pow;
1748 if exp >= BIG_POWERS_10.len() {
1749 pow = Decimal::from(BIG_POWERS_10[BIG_POWERS_10.len() - 1]);
1750 exp -= BIG_POWERS_10.len();
1751 } else {
1752 pow = Decimal::from(BIG_POWERS_10[exp - 1]);
1753 exp = 0;
1754 }
1755 num = num.checked_div(pow)?;
1756 }
1757 let mut num = num.round_dp_with_strategy(0, strategy).trunc();
1758 let mut exp = (mantissa_sf - digits - scale) as usize;
1759 while exp > 0 {
1760 let pow;
1761 if exp >= BIG_POWERS_10.len() {
1762 pow = Decimal::from(BIG_POWERS_10[BIG_POWERS_10.len() - 1]);
1763 exp -= BIG_POWERS_10.len();
1764 } else {
1765 pow = Decimal::from(BIG_POWERS_10[exp - 1]);
1766 exp = 0;
1767 }
1768 num = num.checked_mul(pow)?;
1769 }
1770 Some(num)
1771 } else {
1772 Some(self.round_dp_with_strategy(scale - diff, strategy))
1773 }
1774 }
1775 Ordering::Equal => {
1776 // Case where significant figures = requested significant digits.
1777 Some(*self)
1778 }
1779 }
1780 }
1781
1782 /// Convert `Decimal` to an internal representation of the underlying struct. This is useful
1783 /// for debugging the internal state of the object.
1784 ///
1785 /// # Important Disclaimer
1786 /// This is primarily intended for library maintainers. The internal representation of a
1787 /// `Decimal` is considered "unstable" for public use.
1788 ///
1789 /// # Example
1790 ///
1791 /// ```
1792 /// # use rust_decimal::Decimal;
1793 /// # use rust_decimal_macros::dec;
1794 ///
1795 /// let pi = dec!(3.1415926535897932384626433832);
1796 /// assert_eq!(format!("{:?}", pi), "3.1415926535897932384626433832");
1797 /// assert_eq!(format!("{:?}", pi.unpack()), "UnpackedDecimal { \
1798 /// negative: false, scale: 28, hi: 1703060790, mid: 185874565, lo: 1102470952 \
1799 /// }");
1800 /// ```
1801 #[must_use]
1802 pub const fn unpack(&self) -> UnpackedDecimal {
1803 UnpackedDecimal {
1804 negative: self.is_sign_negative(),
1805 scale: self.scale(),
1806 hi: self.hi,
1807 lo: self.lo,
1808 mid: self.mid,
1809 }
1810 }
1811
1812 #[inline(always)]
1813 pub(crate) const fn lo(&self) -> u32 {
1814 self.lo
1815 }
1816
1817 #[inline(always)]
1818 pub(crate) const fn mid(&self) -> u32 {
1819 self.mid
1820 }
1821
1822 #[inline(always)]
1823 pub(crate) const fn hi(&self) -> u32 {
1824 self.hi
1825 }
1826
1827 #[inline(always)]
1828 pub(crate) const fn flags(&self) -> u32 {
1829 self.flags
1830 }
1831
1832 #[inline(always)]
1833 pub(crate) const fn mantissa_array3(&self) -> [u32; 3] {
1834 [self.lo, self.mid, self.hi]
1835 }
1836
1837 #[inline(always)]
1838 pub(crate) const fn mantissa_array4(&self) -> [u32; 4] {
1839 [self.lo, self.mid, self.hi, 0]
1840 }
1841
1842 /// Parses a 32-bit float into a Decimal number whilst retaining any non-guaranteed precision.
1843 ///
1844 /// Typically when a float is parsed in Rust Decimal, any excess bits (after ~7.22 decimal points for
1845 /// f32 as per IEEE-754) are removed due to any digits following this are considered an approximation
1846 /// at best. This function bypasses this additional step and retains these excess bits.
1847 ///
1848 /// # Example
1849 ///
1850 /// ```
1851 /// # use rust_decimal::prelude::*;
1852 /// #
1853 /// // Usually floats are parsed leveraging float guarantees. i.e. 0.1_f32 => 0.1
1854 /// assert_eq!("0.1", Decimal::from_f32(0.1_f32).unwrap().to_string());
1855 ///
1856 /// // Sometimes, we may want to represent the approximation exactly.
1857 /// assert_eq!("0.100000001490116119384765625", Decimal::from_f32_retain(0.1_f32).unwrap().to_string());
1858 /// ```
1859 pub fn from_f32_retain(n: f32) -> Option<Self> {
1860 from_f32(n, false)
1861 }
1862
1863 /// Parses a 64-bit float into a Decimal number whilst retaining any non-guaranteed precision.
1864 ///
1865 /// Typically when a float is parsed in Rust Decimal, any excess bits (after ~15.95 decimal points for
1866 /// f64 as per IEEE-754) are removed due to any digits following this are considered an approximation
1867 /// at best. This function bypasses this additional step and retains these excess bits.
1868 ///
1869 /// # Example
1870 ///
1871 /// ```
1872 /// # use rust_decimal::prelude::*;
1873 /// #
1874 /// // Usually floats are parsed leveraging float guarantees. i.e. 0.1_f64 => 0.1
1875 /// assert_eq!("0.1", Decimal::from_f64(0.1_f64).unwrap().to_string());
1876 ///
1877 /// // Sometimes, we may want to represent the approximation exactly.
1878 /// assert_eq!("0.1000000000000000055511151231", Decimal::from_f64_retain(0.1_f64).unwrap().to_string());
1879 /// ```
1880 pub fn from_f64_retain(n: f64) -> Option<Self> {
1881 from_f64(n, false)
1882 }
1883}
1884
1885impl Default for Decimal {
1886 /// Returns the default value for a `Decimal` (equivalent to `Decimal::ZERO`). [Read more]
1887 ///
1888 /// [Read more]: core::default::Default#tymethod.default
1889 #[inline]
1890 fn default() -> Self {
1891 ZERO
1892 }
1893}
1894
1895pub(crate) enum CalculationResult {
1896 Ok(Decimal),
1897 Overflow,
1898 DivByZero,
1899}
1900
1901#[inline]
1902const fn flags(neg: bool, scale: u32) -> u32 {
1903 (scale << SCALE_SHIFT) | ((neg as u32) << SIGN_SHIFT)
1904}
1905
1906macro_rules! integer_docs {
1907 ( true ) => {
1908 " by truncating and returning the integer component"
1909 };
1910 ( false ) => {
1911 ""
1912 };
1913}
1914
1915// #[doc] attributes are formatted poorly with rustfmt so skip for now.
1916// See https://github.com/rust-lang/rustfmt/issues/5062 for more information.
1917#[rustfmt::skip]
1918macro_rules! impl_try_from_decimal {
1919 ($TInto:ty, $conversion_fn:path, $additional_docs:expr) => {
1920 #[doc = concat!(
1921 "Try to convert a `Decimal` to `",
1922 stringify!($TInto),
1923 "`",
1924 $additional_docs,
1925 ".\n\nCan fail if the `Decimal` is out of range for `",
1926 stringify!($TInto),
1927 "`.",
1928 )]
1929 impl TryFrom<Decimal> for $TInto {
1930 type Error = crate::Error;
1931
1932 #[inline]
1933 fn try_from(t: Decimal) -> Result<Self, Error> {
1934 $conversion_fn(&t).ok_or_else(|| Error::ConversionTo(stringify!($TInto).into()))
1935 }
1936 }
1937 };
1938}
1939
1940impl_try_from_decimal!(f32, Decimal::to_f32, integer_docs!(false));
1941impl_try_from_decimal!(f64, Decimal::to_f64, integer_docs!(false));
1942impl_try_from_decimal!(isize, Decimal::to_isize, integer_docs!(true));
1943impl_try_from_decimal!(i8, Decimal::to_i8, integer_docs!(true));
1944impl_try_from_decimal!(i16, Decimal::to_i16, integer_docs!(true));
1945impl_try_from_decimal!(i32, Decimal::to_i32, integer_docs!(true));
1946impl_try_from_decimal!(i64, Decimal::to_i64, integer_docs!(true));
1947impl_try_from_decimal!(i128, Decimal::to_i128, integer_docs!(true));
1948impl_try_from_decimal!(usize, Decimal::to_usize, integer_docs!(true));
1949impl_try_from_decimal!(u8, Decimal::to_u8, integer_docs!(true));
1950impl_try_from_decimal!(u16, Decimal::to_u16, integer_docs!(true));
1951impl_try_from_decimal!(u32, Decimal::to_u32, integer_docs!(true));
1952impl_try_from_decimal!(u64, Decimal::to_u64, integer_docs!(true));
1953impl_try_from_decimal!(u128, Decimal::to_u128, integer_docs!(true));
1954
1955// #[doc] attributes are formatted poorly with rustfmt so skip for now.
1956// See https://github.com/rust-lang/rustfmt/issues/5062 for more information.
1957#[rustfmt::skip]
1958macro_rules! impl_try_from_primitive {
1959 ($TFrom:ty, $conversion_fn:path $(, $err:expr)?) => {
1960 #[doc = concat!(
1961 "Try to convert a `",
1962 stringify!($TFrom),
1963 "` into a `Decimal`.\n\nCan fail if the value is out of range for `Decimal`."
1964 )]
1965 impl TryFrom<$TFrom> for Decimal {
1966 type Error = crate::Error;
1967
1968 #[inline]
1969 fn try_from(t: $TFrom) -> Result<Self, Error> {
1970 $conversion_fn(t) $( .ok_or_else(|| $err) )?
1971 }
1972 }
1973 };
1974}
1975
1976impl_try_from_primitive!(f32, Self::from_f32, Error::ConversionTo("Decimal".into()));
1977impl_try_from_primitive!(f64, Self::from_f64, Error::ConversionTo("Decimal".into()));
1978impl_try_from_primitive!(&str, core::str::FromStr::from_str);
1979
1980macro_rules! impl_from {
1981 ($T:ty, $from_ty:path) => {
1982 ///
1983 /// Conversion to `Decimal`.
1984 ///
1985 impl core::convert::From<$T> for Decimal {
1986 #[inline]
1987 fn from(t: $T) -> Self {
1988 $from_ty(t).unwrap()
1989 }
1990 }
1991 };
1992}
1993
1994impl_from!(isize, FromPrimitive::from_isize);
1995impl_from!(i8, FromPrimitive::from_i8);
1996impl_from!(i16, FromPrimitive::from_i16);
1997impl_from!(i32, FromPrimitive::from_i32);
1998impl_from!(i64, FromPrimitive::from_i64);
1999impl_from!(usize, FromPrimitive::from_usize);
2000impl_from!(u8, FromPrimitive::from_u8);
2001impl_from!(u16, FromPrimitive::from_u16);
2002impl_from!(u32, FromPrimitive::from_u32);
2003impl_from!(u64, FromPrimitive::from_u64);
2004
2005impl_from!(i128, FromPrimitive::from_i128);
2006impl_from!(u128, FromPrimitive::from_u128);
2007
2008impl Zero for Decimal {
2009 fn zero() -> Decimal {
2010 ZERO
2011 }
2012
2013 fn is_zero(&self) -> bool {
2014 self.is_zero()
2015 }
2016}
2017
2018impl One for Decimal {
2019 fn one() -> Decimal {
2020 ONE
2021 }
2022}
2023
2024impl Signed for Decimal {
2025 fn abs(&self) -> Self {
2026 self.abs()
2027 }
2028
2029 fn abs_sub(&self, other: &Self) -> Self {
2030 if self <= other {
2031 ZERO
2032 } else {
2033 self - other
2034 }
2035 }
2036
2037 fn signum(&self) -> Self {
2038 if self.is_zero() {
2039 ZERO
2040 } else {
2041 let mut value = ONE;
2042 if self.is_sign_negative() {
2043 value.set_sign_negative(true);
2044 }
2045 value
2046 }
2047 }
2048
2049 fn is_positive(&self) -> bool {
2050 self.is_sign_positive()
2051 }
2052
2053 fn is_negative(&self) -> bool {
2054 self.is_sign_negative()
2055 }
2056}
2057
2058impl Num for Decimal {
2059 type FromStrRadixErr = Error;
2060
2061 fn from_str_radix(str: &str, radix: u32) -> Result<Self, Self::FromStrRadixErr> {
2062 Decimal::from_str_radix(str, radix)
2063 }
2064}
2065
2066impl FromStr for Decimal {
2067 type Err = Error;
2068
2069 fn from_str(value: &str) -> Result<Decimal, Self::Err> {
2070 crate::str::parse_str_radix_10(value)
2071 }
2072}
2073
2074impl FromPrimitive for Decimal {
2075 fn from_i32(n: i32) -> Option<Decimal> {
2076 let flags: u32;
2077 let value_copy: i64;
2078 if n >= 0 {
2079 flags = 0;
2080 value_copy = n as i64;
2081 } else {
2082 flags = SIGN_MASK;
2083 value_copy = -(n as i64);
2084 }
2085 Some(Decimal {
2086 flags,
2087 lo: value_copy as u32,
2088 mid: 0,
2089 hi: 0,
2090 })
2091 }
2092
2093 fn from_i64(n: i64) -> Option<Decimal> {
2094 let flags: u32;
2095 let value_copy: i128;
2096 if n >= 0 {
2097 flags = 0;
2098 value_copy = n as i128;
2099 } else {
2100 flags = SIGN_MASK;
2101 value_copy = -(n as i128);
2102 }
2103 Some(Decimal {
2104 flags,
2105 lo: value_copy as u32,
2106 mid: (value_copy >> 32) as u32,
2107 hi: 0,
2108 })
2109 }
2110
2111 fn from_i128(n: i128) -> Option<Decimal> {
2112 let flags;
2113 let unsigned;
2114 if n >= 0 {
2115 unsigned = n as u128;
2116 flags = 0;
2117 } else {
2118 unsigned = n.unsigned_abs();
2119 flags = SIGN_MASK;
2120 };
2121 // Check if we overflow
2122 if unsigned >> 96 != 0 {
2123 return None;
2124 }
2125 Some(Decimal {
2126 flags,
2127 lo: unsigned as u32,
2128 mid: (unsigned >> 32) as u32,
2129 hi: (unsigned >> 64) as u32,
2130 })
2131 }
2132
2133 fn from_u32(n: u32) -> Option<Decimal> {
2134 Some(Decimal {
2135 flags: 0,
2136 lo: n,
2137 mid: 0,
2138 hi: 0,
2139 })
2140 }
2141
2142 fn from_u64(n: u64) -> Option<Decimal> {
2143 Some(Decimal {
2144 flags: 0,
2145 lo: n as u32,
2146 mid: (n >> 32) as u32,
2147 hi: 0,
2148 })
2149 }
2150
2151 fn from_u128(n: u128) -> Option<Decimal> {
2152 // Check if we overflow
2153 if n >> 96 != 0 {
2154 return None;
2155 }
2156 Some(Decimal {
2157 flags: 0,
2158 lo: n as u32,
2159 mid: (n >> 32) as u32,
2160 hi: (n >> 64) as u32,
2161 })
2162 }
2163
2164 fn from_f32(n: f32) -> Option<Decimal> {
2165 // By default, we remove excess bits. This allows 0.1_f64 == dec!(0.1).
2166 from_f32(n, true)
2167 }
2168
2169 fn from_f64(n: f64) -> Option<Decimal> {
2170 // By default, we remove excess bits. This allows 0.1_f64 == dec!(0.1).
2171 from_f64(n, true)
2172 }
2173}
2174
2175#[inline]
2176fn from_f64(n: f64, remove_excess_bits: bool) -> Option<Decimal> {
2177 // Handle the case if it is NaN, Infinity or -Infinity
2178 if !n.is_finite() {
2179 return None;
2180 }
2181
2182 // It's a shame we can't use a union for this due to it being broken up by bits
2183 // i.e. 1/11/52 (sign, exponent, mantissa)
2184 // See https://en.wikipedia.org/wiki/IEEE_754-1985
2185 // n = (sign*-1) * 2^exp * mantissa
2186 // Decimal of course stores this differently... 10^-exp * significand
2187 let raw = n.to_bits();
2188 let positive = (raw >> 63) == 0;
2189 let biased_exponent = ((raw >> 52) & 0x7FF) as i32;
2190 let mantissa = raw & 0x000F_FFFF_FFFF_FFFF;
2191
2192 // Handle the special zero case
2193 if biased_exponent == 0 && mantissa == 0 {
2194 let mut zero = ZERO;
2195 if !positive {
2196 zero.set_sign_negative(true);
2197 }
2198 return Some(zero);
2199 }
2200
2201 // Get the bits and exponent2
2202 let mut exponent2 = biased_exponent - 1023;
2203 let mut bits = [
2204 (mantissa & 0xFFFF_FFFF) as u32,
2205 ((mantissa >> 32) & 0xFFFF_FFFF) as u32,
2206 0u32,
2207 ];
2208 if biased_exponent == 0 {
2209 // Denormalized number - correct the exponent
2210 exponent2 += 1;
2211 } else {
2212 // Add extra hidden bit to mantissa
2213 bits[1] |= 0x0010_0000;
2214 }
2215
2216 // The act of copying a mantissa as integer bits is equivalent to shifting
2217 // left the mantissa 52 bits. The exponent is reduced to compensate.
2218 exponent2 -= 52;
2219
2220 // Convert to decimal
2221 base2_to_decimal(&mut bits, exponent2, positive, true, remove_excess_bits)
2222}
2223
2224#[inline]
2225fn from_f32(n: f32, remove_excess_bits: bool) -> Option<Decimal> {
2226 // Handle the case if it is NaN, Infinity or -Infinity
2227 if !n.is_finite() {
2228 return None;
2229 }
2230
2231 // It's a shame we can't use a union for this due to it being broken up by bits
2232 // i.e. 1/8/23 (sign, exponent, mantissa)
2233 // See https://en.wikipedia.org/wiki/IEEE_754-1985
2234 // n = (sign*-1) * 2^exp * mantissa
2235 // Decimal of course stores this differently... 10^-exp * significand
2236 let raw = n.to_bits();
2237 let positive = (raw >> 31) == 0;
2238 let biased_exponent = ((raw >> 23) & 0xFF) as i32;
2239 let mantissa = raw & 0x007F_FFFF;
2240
2241 // Handle the special zero case
2242 if biased_exponent == 0 && mantissa == 0 {
2243 let mut zero = ZERO;
2244 if !positive {
2245 zero.set_sign_negative(true);
2246 }
2247 return Some(zero);
2248 }
2249
2250 // Get the bits and exponent2
2251 let mut exponent2 = biased_exponent - 127;
2252 let mut bits = [mantissa, 0u32, 0u32];
2253 if biased_exponent == 0 {
2254 // Denormalized number - correct the exponent
2255 exponent2 += 1;
2256 } else {
2257 // Add extra hidden bit to mantissa
2258 bits[0] |= 0x0080_0000;
2259 }
2260
2261 // The act of copying a mantissa as integer bits is equivalent to shifting
2262 // left the mantissa 23 bits. The exponent is reduced to compensate.
2263 exponent2 -= 23;
2264
2265 // Convert to decimal
2266 base2_to_decimal(&mut bits, exponent2, positive, false, remove_excess_bits)
2267}
2268
2269fn base2_to_decimal(
2270 bits: &mut [u32; 3],
2271 exponent2: i32,
2272 positive: bool,
2273 is64: bool,
2274 remove_excess_bits: bool,
2275) -> Option<Decimal> {
2276 // 2^exponent2 = (10^exponent2)/(5^exponent2)
2277 // = (5^-exponent2)*(10^exponent2)
2278 let mut exponent5 = -exponent2;
2279 let mut exponent10 = exponent2; // Ultimately, we want this for the scale
2280
2281 while exponent5 > 0 {
2282 // Check to see if the mantissa is divisible by 2
2283 if bits[0] & 0x1 == 0 {
2284 exponent10 += 1;
2285 exponent5 -= 1;
2286
2287 // We can divide by 2 without losing precision
2288 let hi_carry = bits[2] & 0x1 == 1;
2289 bits[2] >>= 1;
2290 let mid_carry = bits[1] & 0x1 == 1;
2291 bits[1] = (bits[1] >> 1) | if hi_carry { SIGN_MASK } else { 0 };
2292 bits[0] = (bits[0] >> 1) | if mid_carry { SIGN_MASK } else { 0 };
2293 } else {
2294 // The mantissa is NOT divisible by 2. Therefore the mantissa should
2295 // be multiplied by 5, unless the multiplication overflows.
2296 exponent5 -= 1;
2297
2298 let mut temp = [bits[0], bits[1], bits[2]];
2299 if ops::array::mul_by_u32(&mut temp, 5) == 0 {
2300 // Multiplication succeeded without overflow, so copy result back
2301 bits[0] = temp[0];
2302 bits[1] = temp[1];
2303 bits[2] = temp[2];
2304 } else {
2305 // Multiplication by 5 overflows. The mantissa should be divided
2306 // by 2, and therefore will lose significant digits.
2307 exponent10 += 1;
2308
2309 // Shift right
2310 let hi_carry = bits[2] & 0x1 == 1;
2311 bits[2] >>= 1;
2312 let mid_carry = bits[1] & 0x1 == 1;
2313 bits[1] = (bits[1] >> 1) | if hi_carry { SIGN_MASK } else { 0 };
2314 bits[0] = (bits[0] >> 1) | if mid_carry { SIGN_MASK } else { 0 };
2315 }
2316 }
2317 }
2318
2319 // In order to divide the value by 5, it is best to multiply by 2/10.
2320 // Therefore, exponent10 is decremented, and the mantissa should be multiplied by 2
2321 while exponent5 < 0 {
2322 if bits[2] & SIGN_MASK == 0 {
2323 // No far left bit, the mantissa can withstand a shift-left without overflowing
2324 exponent10 -= 1;
2325 exponent5 += 1;
2326 ops::array::shl1_internal(bits, 0);
2327 } else if exponent10 * 2 > -exponent5 {
2328 // Multiplying by >=2 which, due to the previous condition, means an overflow.
2329 return None;
2330 } else {
2331 // The mantissa would overflow if shifted. Therefore it should be
2332 // directly divided by 5. This will lose significant digits, unless
2333 // by chance the mantissa happens to be divisible by 5.
2334 exponent5 += 1;
2335 ops::array::div_by_u32(bits, 5);
2336 }
2337 }
2338
2339 // At this point, the mantissa has assimilated the exponent5, but
2340 // exponent10 might not be suitable for assignment. exponent10 must be
2341 // in the range [-MAX_SCALE..0], so the mantissa must be scaled up or
2342 // down appropriately.
2343 while exponent10 > 0 {
2344 // In order to bring exponent10 down to 0, the mantissa should be
2345 // multiplied by 10 to compensate. If the exponent10 is too big, this
2346 // will cause the mantissa to overflow.
2347 if ops::array::mul_by_u32(bits, 10) == 0 {
2348 exponent10 -= 1;
2349 } else {
2350 // Overflowed - return?
2351 return None;
2352 }
2353 }
2354
2355 // In order to bring exponent up to -MAX_SCALE, the mantissa should
2356 // be divided by 10 to compensate. If the exponent10 is too small, this
2357 // will cause the mantissa to underflow and become 0.
2358 while exponent10 < -(Decimal::MAX_SCALE as i32) {
2359 let rem10 = ops::array::div_by_u32(bits, 10);
2360 exponent10 += 1;
2361 if ops::array::is_all_zero(bits) {
2362 // Underflow, unable to keep dividing
2363 exponent10 = 0;
2364 } else if rem10 >= 5 {
2365 ops::array::add_one_internal(bits);
2366 }
2367 }
2368
2369 if remove_excess_bits {
2370 // This step is required in order to remove excess bits of precision from the
2371 // end of the bit representation, down to the precision guaranteed by the
2372 // floating point number (see IEEE-754).
2373 if is64 {
2374 // Guaranteed to approx 15/16 dp
2375 while exponent10 < 0 && (bits[2] != 0 || (bits[1] & 0xFFF0_0000) != 0) {
2376 let rem10 = ops::array::div_by_u32(bits, 10);
2377 exponent10 += 1;
2378 if rem10 >= 5 {
2379 ops::array::add_one_internal(bits);
2380 }
2381 }
2382 } else {
2383 // Guaranteed to about 7/8 dp
2384 while exponent10 < 0 && ((bits[0] & 0xFF00_0000) != 0 || bits[1] != 0 || bits[2] != 0) {
2385 let rem10 = ops::array::div_by_u32(bits, 10);
2386 exponent10 += 1;
2387 if rem10 >= 5 {
2388 ops::array::add_one_internal(bits);
2389 }
2390 }
2391 }
2392
2393 // Remove multiples of 10 from the representation
2394 while exponent10 < 0 {
2395 let mut temp = [bits[0], bits[1], bits[2]];
2396 let remainder = ops::array::div_by_u32(&mut temp, 10);
2397 if remainder == 0 {
2398 exponent10 += 1;
2399 bits[0] = temp[0];
2400 bits[1] = temp[1];
2401 bits[2] = temp[2];
2402 } else {
2403 break;
2404 }
2405 }
2406 }
2407
2408 Some(Decimal {
2409 lo: bits[0],
2410 mid: bits[1],
2411 hi: bits[2],
2412 flags: flags(!positive, -exponent10 as u32),
2413 })
2414}
2415
2416impl Decimal {
2417 /// Converts this `Decimal` to an `i128`, truncating any fractional part.
2418 ///
2419 /// This is the infallible equivalent of [`ToPrimitive::to_i128`].
2420 pub fn as_i128(&self) -> i128 {
2421 let d = self.trunc();
2422 let raw: i128 = ((i128::from(d.hi) << 64) | (i128::from(d.mid) << 32)) | i128::from(d.lo);
2423 if self.is_sign_negative() {
2424 -raw
2425 } else {
2426 raw
2427 }
2428 }
2429
2430 /// Converts this `Decimal` to an `f64`.
2431 ///
2432 /// This is the infallible equivalent of [`ToPrimitive::to_f64`].
2433 pub fn as_f64(&self) -> f64 {
2434 if self.scale() == 0 {
2435 // If scale is zero, we are storing a 96-bit integer value, that would
2436 // always fit into i128, which in turn is always representable as f64,
2437 // albeit with loss of precision for values outside of -2^53..2^53 range.
2438 self.as_i128() as f64
2439 } else {
2440 let neg = self.is_sign_negative();
2441 let mut mantissa: u128 = self.lo.into();
2442 mantissa |= (self.mid as u128) << 32;
2443 mantissa |= (self.hi as u128) << 64;
2444 // scale is at most 28, so this fits comfortably into a u128.
2445 let scale = self.scale();
2446 let precision: u128 = 10_u128.pow(scale);
2447 let integral_part = mantissa / precision;
2448 let frac_part = mantissa % precision;
2449 let frac_f64 = (frac_part as f64) / (precision as f64);
2450 let integral = integral_part as f64;
2451 // If there is a fractional component then we will need to add that and remove any
2452 // inaccuracies that creep in during addition. Otherwise, if the fractional component
2453 // is zero we can exit early.
2454 if frac_f64.is_zero() {
2455 if neg {
2456 return -integral;
2457 }
2458 return integral;
2459 }
2460 let value = integral + frac_f64;
2461 let round_to = 10f64.powi(self.scale() as i32);
2462 let rounded = (value * round_to).round() / round_to;
2463 if neg {
2464 -rounded
2465 } else {
2466 rounded
2467 }
2468 }
2469 }
2470}
2471
2472impl ToPrimitive for Decimal {
2473 fn to_i64(&self) -> Option<i64> {
2474 let d = self.trunc();
2475 // If it is in the hi bit then it is a clear overflow.
2476 if d.hi != 0 {
2477 // Overflow
2478 return None;
2479 }
2480 let negative = self.is_sign_negative();
2481
2482 // A bit more convoluted in terms of checking when it comes to the hi bit due to twos-complement
2483 if d.mid & 0x8000_0000 > 0 {
2484 if negative && d.mid == 0x8000_0000 && d.lo == 0 {
2485 // We do this because below we try to convert the i64 to a positive first - of which
2486 // doesn't fit into an i64.
2487 return Some(i64::MIN);
2488 }
2489 return None;
2490 }
2491
2492 let raw: i64 = (i64::from(d.mid) << 32) | i64::from(d.lo);
2493 if negative {
2494 Some(raw.neg())
2495 } else {
2496 Some(raw)
2497 }
2498 }
2499
2500 fn to_i128(&self) -> Option<i128> {
2501 Some(self.as_i128())
2502 }
2503
2504 fn to_u64(&self) -> Option<u64> {
2505 if self.is_sign_negative() {
2506 return None;
2507 }
2508
2509 let d = self.trunc();
2510 if d.hi != 0 {
2511 // Overflow
2512 return None;
2513 }
2514
2515 Some((u64::from(d.mid) << 32) | u64::from(d.lo))
2516 }
2517
2518 fn to_u128(&self) -> Option<u128> {
2519 if self.is_sign_negative() {
2520 return None;
2521 }
2522
2523 let d = self.trunc();
2524 Some((u128::from(d.hi) << 64) | (u128::from(d.mid) << 32) | u128::from(d.lo))
2525 }
2526
2527 fn to_f64(&self) -> Option<f64> {
2528 Some(self.as_f64())
2529 }
2530}
2531
2532impl fmt::Display for Decimal {
2533 fn fmt(&self, f: &mut fmt::Formatter) -> Result<(), fmt::Error> {
2534 let (rep, additional) = crate::str::to_str_internal(self, false, f.precision());
2535 if let Some(additional) = additional {
2536 let value = [rep.as_str(), "0".repeat(additional).as_str()].concat();
2537 f.pad_integral(self.is_sign_positive(), "", value.as_str())
2538 } else {
2539 f.pad_integral(self.is_sign_positive(), "", rep.as_str())
2540 }
2541 }
2542}
2543
2544impl fmt::Debug for Decimal {
2545 fn fmt(&self, f: &mut fmt::Formatter) -> Result<(), fmt::Error> {
2546 fmt::Display::fmt(self, f)
2547 }
2548}
2549
2550impl fmt::LowerExp for Decimal {
2551 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
2552 crate::str::fmt_scientific_notation(self, "e", f)
2553 }
2554}
2555
2556impl fmt::UpperExp for Decimal {
2557 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
2558 crate::str::fmt_scientific_notation(self, "E", f)
2559 }
2560}
2561
2562impl Neg for Decimal {
2563 type Output = Decimal;
2564
2565 fn neg(self) -> Decimal {
2566 let mut copy = self;
2567 copy.set_sign_negative(self.is_sign_positive());
2568 copy
2569 }
2570}
2571
2572impl Neg for &Decimal {
2573 type Output = Decimal;
2574
2575 fn neg(self) -> Decimal {
2576 Decimal {
2577 flags: flags(!self.is_sign_negative(), self.scale()),
2578 hi: self.hi,
2579 lo: self.lo,
2580 mid: self.mid,
2581 }
2582 }
2583}
2584
2585impl AddAssign for Decimal {
2586 fn add_assign(&mut self, other: Decimal) {
2587 let result = self.add(other);
2588 self.lo = result.lo;
2589 self.mid = result.mid;
2590 self.hi = result.hi;
2591 self.flags = result.flags;
2592 }
2593}
2594
2595impl<'a> AddAssign<&'a Decimal> for Decimal {
2596 fn add_assign(&mut self, other: &'a Decimal) {
2597 Decimal::add_assign(self, *other)
2598 }
2599}
2600
2601impl AddAssign<Decimal> for &mut Decimal {
2602 fn add_assign(&mut self, other: Decimal) {
2603 Decimal::add_assign(*self, other)
2604 }
2605}
2606
2607impl<'a> AddAssign<&'a Decimal> for &'a mut Decimal {
2608 fn add_assign(&mut self, other: &'a Decimal) {
2609 Decimal::add_assign(*self, *other)
2610 }
2611}
2612
2613impl SubAssign for Decimal {
2614 fn sub_assign(&mut self, other: Decimal) {
2615 let result = self.sub(other);
2616 self.lo = result.lo;
2617 self.mid = result.mid;
2618 self.hi = result.hi;
2619 self.flags = result.flags;
2620 }
2621}
2622
2623impl<'a> SubAssign<&'a Decimal> for Decimal {
2624 fn sub_assign(&mut self, other: &'a Decimal) {
2625 Decimal::sub_assign(self, *other)
2626 }
2627}
2628
2629impl SubAssign<Decimal> for &mut Decimal {
2630 fn sub_assign(&mut self, other: Decimal) {
2631 Decimal::sub_assign(*self, other)
2632 }
2633}
2634
2635impl<'a> SubAssign<&'a Decimal> for &'a mut Decimal {
2636 fn sub_assign(&mut self, other: &'a Decimal) {
2637 Decimal::sub_assign(*self, *other)
2638 }
2639}
2640
2641impl MulAssign for Decimal {
2642 fn mul_assign(&mut self, other: Decimal) {
2643 let result = self.mul(other);
2644 self.lo = result.lo;
2645 self.mid = result.mid;
2646 self.hi = result.hi;
2647 self.flags = result.flags;
2648 }
2649}
2650
2651impl<'a> MulAssign<&'a Decimal> for Decimal {
2652 fn mul_assign(&mut self, other: &'a Decimal) {
2653 Decimal::mul_assign(self, *other)
2654 }
2655}
2656
2657impl MulAssign<Decimal> for &mut Decimal {
2658 fn mul_assign(&mut self, other: Decimal) {
2659 Decimal::mul_assign(*self, other)
2660 }
2661}
2662
2663impl<'a> MulAssign<&'a Decimal> for &'a mut Decimal {
2664 fn mul_assign(&mut self, other: &'a Decimal) {
2665 Decimal::mul_assign(*self, *other)
2666 }
2667}
2668
2669impl DivAssign for Decimal {
2670 fn div_assign(&mut self, other: Decimal) {
2671 let result = self.div(other);
2672 self.lo = result.lo;
2673 self.mid = result.mid;
2674 self.hi = result.hi;
2675 self.flags = result.flags;
2676 }
2677}
2678
2679impl<'a> DivAssign<&'a Decimal> for Decimal {
2680 fn div_assign(&mut self, other: &'a Decimal) {
2681 Decimal::div_assign(self, *other)
2682 }
2683}
2684
2685impl DivAssign<Decimal> for &mut Decimal {
2686 fn div_assign(&mut self, other: Decimal) {
2687 Decimal::div_assign(*self, other)
2688 }
2689}
2690
2691impl<'a> DivAssign<&'a Decimal> for &'a mut Decimal {
2692 fn div_assign(&mut self, other: &'a Decimal) {
2693 Decimal::div_assign(*self, *other)
2694 }
2695}
2696
2697impl RemAssign for Decimal {
2698 fn rem_assign(&mut self, other: Decimal) {
2699 let result = self.rem(other);
2700 self.lo = result.lo;
2701 self.mid = result.mid;
2702 self.hi = result.hi;
2703 self.flags = result.flags;
2704 }
2705}
2706
2707impl<'a> RemAssign<&'a Decimal> for Decimal {
2708 fn rem_assign(&mut self, other: &'a Decimal) {
2709 Decimal::rem_assign(self, *other)
2710 }
2711}
2712
2713impl RemAssign<Decimal> for &mut Decimal {
2714 fn rem_assign(&mut self, other: Decimal) {
2715 Decimal::rem_assign(*self, other)
2716 }
2717}
2718
2719impl<'a> RemAssign<&'a Decimal> for &'a mut Decimal {
2720 fn rem_assign(&mut self, other: &'a Decimal) {
2721 Decimal::rem_assign(*self, *other)
2722 }
2723}
2724
2725impl PartialEq for Decimal {
2726 #[inline]
2727 fn eq(&self, other: &Decimal) -> bool {
2728 self.cmp(other) == Equal
2729 }
2730}
2731
2732impl Eq for Decimal {}
2733
2734impl Hash for Decimal {
2735 fn hash<H: Hasher>(&self, state: &mut H) {
2736 let n = self.normalize();
2737 n.lo.hash(state);
2738 n.mid.hash(state);
2739 n.hi.hash(state);
2740 n.flags.hash(state);
2741 }
2742}
2743
2744impl PartialOrd for Decimal {
2745 #[inline]
2746 fn partial_cmp(&self, other: &Decimal) -> Option<Ordering> {
2747 Some(self.cmp(other))
2748 }
2749}
2750
2751impl Ord for Decimal {
2752 fn cmp(&self, other: &Decimal) -> Ordering {
2753 ops::cmp_impl(self, other)
2754 }
2755}
2756
2757impl Product for Decimal {
2758 /// Panics if out-of-bounds
2759 fn product<I: Iterator<Item = Decimal>>(iter: I) -> Self {
2760 let mut product = ONE;
2761 for i in iter {
2762 product *= i;
2763 }
2764 product
2765 }
2766}
2767
2768impl<'a> Product<&'a Decimal> for Decimal {
2769 /// Panics if out-of-bounds
2770 fn product<I: Iterator<Item = &'a Decimal>>(iter: I) -> Self {
2771 let mut product = ONE;
2772 for i in iter {
2773 product *= i;
2774 }
2775 product
2776 }
2777}
2778
2779impl Sum for Decimal {
2780 fn sum<I: Iterator<Item = Decimal>>(iter: I) -> Self {
2781 let mut sum = ZERO;
2782 for i in iter {
2783 sum += i;
2784 }
2785 sum
2786 }
2787}
2788
2789impl<'a> Sum<&'a Decimal> for Decimal {
2790 fn sum<I: Iterator<Item = &'a Decimal>>(iter: I) -> Self {
2791 let mut sum = ZERO;
2792 for i in iter {
2793 sum += i;
2794 }
2795 sum
2796 }
2797}
2798
2799#[cfg(test)]
2800mod tests {
2801 use super::*;
2802
2803 #[test]
2804 fn from_scientific_0e0() {
2805 let dec = Decimal::from_scientific("0e0").unwrap();
2806 assert_eq!(dec, Decimal::ZERO);
2807 }
2808}