22
22
23
23
use libc:: c_int;
24
24
use num:: { Zero , One , strconv} ;
25
+ use num:: FPCategory ;
25
26
use prelude:: * ;
26
27
27
28
pub use f64:: { add, sub, mul, div, rem, lt, le, eq, ne, ge, gt} ;
@@ -782,32 +783,37 @@ impl Primitive for float {
782
783
783
784
impl Float for float {
784
785
#[inline(always)]
785
- fn NaN() -> float { 0.0 / 0.0 }
786
+ fn NaN() -> float { Float::NaN::<f64>() as float }
786
787
787
788
#[inline(always)]
788
- fn infinity() -> float { 1.0 / 0.0 }
789
+ fn infinity() -> float { Float::infinity::<f64>() as float }
789
790
790
791
#[inline(always)]
791
- fn neg_infinity() -> float { -1.0 / 0.0 }
792
+ fn neg_infinity() -> float { Float::neg_infinity::<f64>() as float }
792
793
793
794
#[inline(always)]
794
- fn neg_zero() -> float { -0.0 }
795
+ fn neg_zero() -> float { Float::neg_zero::<f64>() as float }
795
796
796
797
/// Returns `true` if the number is NaN
797
798
#[inline(always)]
798
- fn is_NaN(&self) -> bool { *self != *self }
799
+ fn is_NaN(&self) -> bool { ( *self as f64).is_NaN() }
799
800
800
801
/// Returns `true` if the number is infinite
801
802
#[inline(always)]
802
- fn is_infinite(&self) -> bool {
803
- *self == Float::infinity() || *self == Float::neg_infinity()
804
- }
803
+ fn is_infinite(&self) -> bool { (*self as f64).is_infinite() }
805
804
806
- /// Returns `true` if the number is not infinite or NaN
805
+ /// Returns `true` if the number is neither infinite or NaN
807
806
#[inline(always)]
808
- fn is_finite(&self) -> bool {
809
- !(self.is_NaN() || self.is_infinite())
810
- }
807
+ fn is_finite(&self) -> bool { (*self as f64).is_finite() }
808
+
809
+ /// Returns `true` if the number is neither zero, infinite, subnormal or NaN
810
+ #[inline(always)]
811
+ fn is_normal(&self) -> bool { (*self as f64).is_normal() }
812
+
813
+ /// Returns the floating point category of the number. If only one property is going to
814
+ /// be tested, it is generally faster to use the specific predicate instead.
815
+ #[inline(always)]
816
+ fn classify(&self) -> FPCategory { (*self as f64).classify() }
811
817
812
818
#[inline(always)]
813
819
fn mantissa_digits() -> uint { Float::mantissa_digits::<f64>() }
@@ -844,9 +850,7 @@ impl Float for float {
844
850
/// than if the operations were performed separately
845
851
///
846
852
#[inline(always)]
847
- fn ln_1p(&self) -> float {
848
- (*self as f64).ln_1p() as float
849
- }
853
+ fn ln_1p(&self) -> float { (*self as f64).ln_1p() as float }
850
854
851
855
///
852
856
/// Fused multiply-add. Computes `(self * a) + b` with only one rounding error. This
@@ -867,6 +871,7 @@ impl Float for float {
867
871
868
872
#[cfg(test)]
869
873
mod tests {
874
+ use num::*;
870
875
use super::*;
871
876
use prelude::*;
872
877
@@ -1063,6 +1068,30 @@ mod tests {
1063
1068
assert_eq!(Primitive::bytes::<float>(), sys::size_of::<float>());
1064
1069
}
1065
1070
1071
+ #[test]
1072
+ fn test_is_normal() {
1073
+ assert!(!Float::NaN::<float>().is_normal());
1074
+ assert!(!Float::infinity::<float>().is_normal());
1075
+ assert!(!Float::neg_infinity::<float>().is_normal());
1076
+ assert!(!Zero::zero::<float>().is_normal());
1077
+ assert!(!Float::neg_zero::<float>().is_normal());
1078
+ assert!(1f.is_normal());
1079
+ assert!(1e-307f.is_normal());
1080
+ assert!(!1e-308f.is_normal());
1081
+ }
1082
+
1083
+ #[test]
1084
+ fn test_classify() {
1085
+ assert_eq!(Float::NaN::<float>().classify(), FPNaN);
1086
+ assert_eq!(Float::infinity::<float>().classify(), FPInfinite);
1087
+ assert_eq!(Float::neg_infinity::<float>().classify(), FPInfinite);
1088
+ assert_eq!(Zero::zero::<float>().classify(), FPZero);
1089
+ assert_eq!(Float::neg_zero::<float>().classify(), FPZero);
1090
+ assert_eq!(1f.classify(), FPNormal);
1091
+ assert_eq!(1e-307f.classify(), FPNormal);
1092
+ assert_eq!(1e-308f.classify(), FPSubnormal);
1093
+ }
1094
+
1066
1095
#[test]
1067
1096
pub fn test_to_str_exact_do_decimal() {
1068
1097
let s = to_str_exact(5.0, 4u);
0 commit comments