diff options
| author | bors <bors@rust-lang.org> | 2019-04-25 17:26:20 +0000 |
|---|---|---|
| committer | bors <bors@rust-lang.org> | 2019-04-25 17:26:20 +0000 |
| commit | c32171bd5efedd58fd471c21802e23005c2918fc (patch) | |
| tree | c792b35572465de3c7edb85f7faf73a7f9ce1567 /src/libcore | |
| parent | bd31c392f286d61caac0babee68c900cdaa8b504 (diff) | |
| parent | c7d47c8cf4cd4db4226a38884a2d5fad371d9330 (diff) | |
| download | rust-c32171bd5efedd58fd471c21802e23005c2918fc.tar.gz rust-c32171bd5efedd58fd471c21802e23005c2918fc.zip | |
Auto merge of #60192 - t-rapp:tr-saturating-funcs, r=alexcrichton
Implement saturating_abs() and saturating_neg() functions for signed integer types Similar to wrapping_abs() / wrapping_neg() functions but saturating at the numeric bounds instead of wrapping around. Complements the existing set of functions with saturation mechanics. cc #59983
Diffstat (limited to 'src/libcore')
| -rw-r--r-- | src/libcore/num/mod.rs | 56 | ||||
| -rw-r--r-- | src/libcore/tests/lib.rs | 1 | ||||
| -rw-r--r-- | src/libcore/tests/num/int_macros.rs | 26 |
3 files changed, 83 insertions, 0 deletions
diff --git a/src/libcore/num/mod.rs b/src/libcore/num/mod.rs index f1325f383ee..718222ee0f4 100644 --- a/src/libcore/num/mod.rs +++ b/src/libcore/num/mod.rs @@ -959,6 +959,62 @@ $EndFeature, " } doc_comment! { + concat!("Saturating integer negation. Computes `-self`, returning `MAX` if `self == MIN` +instead of overflowing. + +# Examples + +Basic usage: + +``` +", $Feature, "#![feature(saturating_neg)] +assert_eq!(100", stringify!($SelfT), ".saturating_neg(), -100); +assert_eq!((-100", stringify!($SelfT), ").saturating_neg(), 100); +assert_eq!(", stringify!($SelfT), "::min_value().saturating_neg(), ", stringify!($SelfT), +"::max_value()); +assert_eq!(", stringify!($SelfT), "::max_value().saturating_neg(), ", stringify!($SelfT), +"::min_value() + 1);", +$EndFeature, " +```"), + + #[unstable(feature = "saturating_neg", issue = "59983")] + #[inline] + pub fn saturating_neg(self) -> Self { + intrinsics::saturating_sub(0, self) + } + } + + doc_comment! { + concat!("Saturating absolute value. Computes `self.abs()`, returning `MAX` if `self == +MIN` instead of overflowing. + +# Examples + +Basic usage: + +``` +", $Feature, "#![feature(saturating_neg)] +assert_eq!(100", stringify!($SelfT), ".saturating_abs(), 100); +assert_eq!((-100", stringify!($SelfT), ").saturating_abs(), 100); +assert_eq!(", stringify!($SelfT), "::min_value().saturating_abs(), ", stringify!($SelfT), +"::max_value()); +assert_eq!((", stringify!($SelfT), "::min_value() + 1).saturating_abs(), ", stringify!($SelfT), +"::max_value());", +$EndFeature, " +```"), + + #[unstable(feature = "saturating_neg", issue = "59983")] + #[inline] + pub fn saturating_abs(self) -> Self { + if self.is_negative() { + self.saturating_neg() + } else { + self + } + } + } + + doc_comment! { concat!("Saturating integer multiplication. Computes `self * rhs`, saturating at the numeric bounds instead of overflowing. diff --git a/src/libcore/tests/lib.rs b/src/libcore/tests/lib.rs index 2e4a8a15d20..a3d294e77d3 100644 --- a/src/libcore/tests/lib.rs +++ b/src/libcore/tests/lib.rs @@ -16,6 +16,7 @@ #![feature(pattern)] #![feature(range_is_empty)] #![feature(raw)] +#![feature(saturating_neg)] #![feature(slice_patterns)] #![feature(sort_internals)] #![feature(slice_partition_at_index)] diff --git a/src/libcore/tests/num/int_macros.rs b/src/libcore/tests/num/int_macros.rs index 92409465d7f..0475aeb96ab 100644 --- a/src/libcore/tests/num/int_macros.rs +++ b/src/libcore/tests/num/int_macros.rs @@ -154,6 +154,32 @@ mod tests { } #[test] + fn test_saturating_abs() { + assert_eq!((0 as $T).saturating_abs(), 0); + assert_eq!((123 as $T).saturating_abs(), 123); + assert_eq!((-123 as $T).saturating_abs(), 123); + assert_eq!((MAX - 2).saturating_abs(), MAX - 2); + assert_eq!((MAX - 1).saturating_abs(), MAX - 1); + assert_eq!(MAX.saturating_abs(), MAX); + assert_eq!((MIN + 2).saturating_abs(), MAX - 1); + assert_eq!((MIN + 1).saturating_abs(), MAX); + assert_eq!(MIN.saturating_abs(), MAX); + } + + #[test] + fn test_saturating_neg() { + assert_eq!((0 as $T).saturating_neg(), 0); + assert_eq!((123 as $T).saturating_neg(), -123); + assert_eq!((-123 as $T).saturating_neg(), 123); + assert_eq!((MAX - 2).saturating_neg(), MIN + 3); + assert_eq!((MAX - 1).saturating_neg(), MIN + 2); + assert_eq!(MAX.saturating_neg(), MIN + 1); + assert_eq!((MIN + 2).saturating_neg(), MAX - 1); + assert_eq!((MIN + 1).saturating_neg(), MAX); + assert_eq!(MIN.saturating_neg(), MAX); + } + + #[test] fn test_from_str() { fn from_str<T: ::std::str::FromStr>(t: &str) -> Option<T> { ::std::str::FromStr::from_str(t).ok() |
