Skip to content

Commit 4bdceb9

Browse files
committed
auto merge of #8459 : thestinger/rust/checked, r=graydon
2 parents 2246d56 + b244911 commit 4bdceb9

File tree

3 files changed

+42
-2
lines changed

3 files changed

+42
-2
lines changed

src/libstd/num/int_macros.rs

Lines changed: 20 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -17,7 +17,7 @@ macro_rules! int_module (($T:ty, $bits:expr) => (mod generated {
1717
#[allow(non_uppercase_statics)];
1818

1919
use num::{ToStrRadix, FromStrRadix};
20-
use num::{Zero, One, strconv};
20+
use num::{CheckedDiv, Zero, One, strconv};
2121
use prelude::*;
2222
use str;
2323

@@ -29,6 +29,17 @@ pub static bytes : uint = ($bits / 8);
2929
pub static min_value: $T = (-1 as $T) << (bits - 1);
3030
pub static max_value: $T = min_value - 1 as $T;
3131

32+
impl CheckedDiv for $T {
33+
#[inline]
34+
fn checked_div(&self, v: &$T) -> Option<$T> {
35+
if *v == 0 || (*self == min_value && *v == -1) {
36+
None
37+
} else {
38+
Some(self / *v)
39+
}
40+
}
41+
}
42+
3243
enum Range { Closed, HalfOpen }
3344

3445
#[inline]
@@ -551,6 +562,7 @@ mod tests {
551562
use super::*;
552563
use prelude::*;
553564
565+
use int;
554566
use i16;
555567
use i32;
556568
use i64;
@@ -921,6 +933,13 @@ mod tests {
921933
fn test_range_step_zero_step() {
922934
do range_step(0,10,0) |_i| { true };
923935
}
936+
937+
#[test]
938+
fn test_signed_checked_div() {
939+
assert_eq!(10i.checked_div(&2), Some(5));
940+
assert_eq!(5i.checked_div(&0), None);
941+
assert_eq!(int::min_value.checked_div(&-1), None);
942+
}
924943
}
925944

926945
}))

src/libstd/num/num.rs

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -892,6 +892,10 @@ impl CheckedMul for uint {
892892
}
893893
}
894894

895+
pub trait CheckedDiv: Div<Self, Self> {
896+
fn checked_div(&self, v: &Self) -> Option<Self>;
897+
}
898+
895899
/// Helper function for testing numeric operations
896900
#[cfg(test)]
897901
pub fn test_num<T:Num + NumCast>(ten: T, two: T) {

src/libstd/num/uint_macros.rs

Lines changed: 18 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -18,7 +18,7 @@ macro_rules! uint_module (($T:ty, $T_SIGNED:ty, $bits:expr) => (mod generated {
1818

1919
use num::BitCount;
2020
use num::{ToStrRadix, FromStrRadix};
21-
use num::{Zero, One, strconv};
21+
use num::{CheckedDiv, Zero, One, strconv};
2222
use prelude::*;
2323
use str;
2424

@@ -30,6 +30,17 @@ pub static bytes : uint = ($bits / 8);
3030
pub static min_value: $T = 0 as $T;
3131
pub static max_value: $T = 0 as $T - 1 as $T;
3232

33+
impl CheckedDiv for $T {
34+
#[inline]
35+
fn checked_div(&self, v: &$T) -> Option<$T> {
36+
if *v == 0 {
37+
None
38+
} else {
39+
Some(self / *v)
40+
}
41+
}
42+
}
43+
3344
enum Range { Closed, HalfOpen }
3445

3546
#[inline]
@@ -694,6 +705,12 @@ mod tests {
694705
fn test_range_step_zero_step_down() {
695706
do range_step(0,-10,0) |_i| { true };
696707
}
708+
709+
#[test]
710+
fn test_unsigned_checked_div() {
711+
assert_eq!(10u.checked_div(&2), Some(5));
712+
assert_eq!(5u.checked_div(&0), None);
713+
}
697714
}
698715

699716
}))

0 commit comments

Comments
 (0)