diff --git a/src/libextra/arena.rs b/src/libextra/arena.rs index 2926d5958f16c..1364f2a828ba5 100644 --- a/src/libextra/arena.rs +++ b/src/libextra/arena.rs @@ -171,7 +171,7 @@ impl Arena { fn alloc_pod_grow(&mut self, n_bytes: uint, align: uint) -> *u8 { // Allocate a new chunk. let chunk_size = at_vec::capacity(self.pod_head.data); - let new_min_chunk_size = uint::max(n_bytes, chunk_size); + let new_min_chunk_size = n_bytes.max(&chunk_size); self.chunks = @mut MutCons(copy self.pod_head, self.chunks); self.pod_head = chunk(uint::next_power_of_two(new_min_chunk_size + 1u), true); @@ -215,7 +215,7 @@ impl Arena { -> (*u8, *u8) { // Allocate a new chunk. let chunk_size = at_vec::capacity(self.head.data); - let new_min_chunk_size = uint::max(n_bytes, chunk_size); + let new_min_chunk_size = n_bytes.max(&chunk_size); self.chunks = @mut MutCons(copy self.head, self.chunks); self.head = chunk(uint::next_power_of_two(new_min_chunk_size + 1u), false); diff --git a/src/libextra/bitv.rs b/src/libextra/bitv.rs index e3a15f76c786b..7bfb6718819b8 100644 --- a/src/libextra/bitv.rs +++ b/src/libextra/bitv.rs @@ -725,7 +725,7 @@ impl Set for BitvSet { } let nbits = self.capacity(); if value >= nbits { - let newsize = uint::max(value, nbits * 2) / uint::bits + 1; + let newsize = value.max(&(nbits * 2)) / uint::bits + 1; assert!(newsize > self.bitv.storage.len()); self.bitv.storage.grow(newsize, &0); } @@ -824,8 +824,7 @@ impl BitvSet { /// and w1/w2 are the words coming from the two vectors self, other. fn each_common(&self, other: &BitvSet, f: &fn(uint, uint, uint) -> bool) -> bool { - let min = uint::min(self.bitv.storage.len(), - other.bitv.storage.len()); + let min = self.bitv.storage.len().min(&other.bitv.storage.len()); self.bitv.storage.slice(0, min).eachi(|i, &w| { f(i * uint::bits, w, other.bitv.storage[i]) }) @@ -842,7 +841,7 @@ impl BitvSet { f: &fn(bool, uint, uint) -> bool) -> bool { let len1 = self.bitv.storage.len(); let len2 = other.bitv.storage.len(); - let min = uint::min(len1, len2); + let min = len1.min(&len2); /* only one of these loops will execute and that's the point */ for self.bitv.storage.slice(min, len1).eachi |i, &w| { diff --git a/src/libextra/net_tcp.rs b/src/libextra/net_tcp.rs index 87ebfdfb7976c..e645c305c39bd 100644 --- a/src/libextra/net_tcp.rs +++ b/src/libextra/net_tcp.rs @@ -29,7 +29,6 @@ use core::comm::{stream, Port, SharedChan}; use core::ptr; use core::result::{Result}; use core::result; -use core::uint; use core::vec; pub mod rustrt { @@ -884,7 +883,7 @@ impl io::Reader for TcpSocketBuf { let needed = len - count; if nbuffered > 0 { unsafe { - let ncopy = uint::min(nbuffered, needed); + let ncopy = nbuffered.min(&needed); let dst = ptr::mut_offset( vec::raw::to_mut_ptr(buf), count); let src = ptr::offset( diff --git a/src/libextra/num/bigint.rs b/src/libextra/num/bigint.rs index 1411079d52f0d..2b7c06a378fd4 100644 --- a/src/libextra/num/bigint.rs +++ b/src/libextra/num/bigint.rs @@ -21,7 +21,6 @@ A BigInt is a combination of BigUint and Sign. use core::prelude::*; use core::iterator::IteratorUtil; use core::cmp::{Eq, Ord, TotalEq, TotalOrd, Ordering, Less, Equal, Greater}; -use core::int; use core::num::{IntConvertible, Zero, One, ToStrRadix, FromStrRadix, Orderable}; use core::str; use core::uint; @@ -60,19 +59,16 @@ pub mod BigDigit { priv static hi_mask: uint = (-1 as uint) << bits; priv static lo_mask: uint = (-1 as uint) >> bits; - priv fn get_hi(n: uint) -> BigDigit { (n >> bits) as BigDigit } priv fn get_lo(n: uint) -> BigDigit { (n & lo_mask) as BigDigit } /// Split one machine sized unsigned integer into two BigDigits. - pub fn from_uint(n: uint) -> (BigDigit, BigDigit) { (get_hi(n), get_lo(n)) } /// Join two BigDigits into one machine sized unsigned integer - pub fn to_uint(hi: BigDigit, lo: BigDigit) -> uint { (lo as uint) | ((hi as uint) << bits) } @@ -90,21 +86,18 @@ pub struct BigUint { } impl Eq for BigUint { - fn eq(&self, other: &BigUint) -> bool { self.equals(other) } fn ne(&self, other: &BigUint) -> bool { !self.equals(other) } } impl TotalEq for BigUint { - fn equals(&self, other: &BigUint) -> bool { match self.cmp(other) { Equal => true, _ => false } } } impl Ord for BigUint { - fn lt(&self, other: &BigUint) -> bool { match self.cmp(other) { Less => true, _ => false} } @@ -123,7 +116,6 @@ impl Ord for BigUint { } impl TotalOrd for BigUint { - fn cmp(&self, other: &BigUint) -> Ordering { let (s_len, o_len) = (self.data.len(), other.data.len()); if s_len < o_len { return Less; } @@ -138,12 +130,10 @@ impl TotalOrd for BigUint { } impl ToStr for BigUint { - fn to_str(&self) -> ~str { self.to_str_radix(10) } } impl FromStr for BigUint { - fn from_str(s: &str) -> Option { FromStrRadix::from_str_radix(s, 10) } @@ -152,60 +142,56 @@ impl FromStr for BigUint { impl Num for BigUint {} impl Orderable for BigUint { - - fn min(&self, other: &BigUint) -> BigUint { + pub fn min(&self, other: &BigUint) -> BigUint { if self < other { self.clone() } else { other.clone() } } - - fn max(&self, other: &BigUint) -> BigUint { + pub fn max(&self, other: &BigUint) -> BigUint { if self > other { self.clone() } else { other.clone() } } - - fn clamp(&self, mn: &BigUint, mx: &BigUint) -> BigUint { - if self > mx { mx.clone() } else - if self < mn { mn.clone() } else { self.clone() } + pub fn clamp(&self, mn: &BigUint, mx: &BigUint) -> BigUint { + cond!( + (self > mx) { mx.clone() } + (self < mn) { mn.clone() } + _ { self.clone() } + ) } } impl Shl for BigUint { - fn shl(&self, rhs: &uint) -> BigUint { let n_unit = *rhs / BigDigit::bits; let n_bits = *rhs % BigDigit::bits; - return self.shl_unit(n_unit).shl_bits(n_bits); + + self.shl_unit(n_unit).shl_bits(n_bits) } } impl Shr for BigUint { - fn shr(&self, rhs: &uint) -> BigUint { let n_unit = *rhs / BigDigit::bits; let n_bits = *rhs % BigDigit::bits; - return self.shr_unit(n_unit).shr_bits(n_bits); + + self.shr_unit(n_unit).shr_bits(n_bits) } } impl Zero for BigUint { + pub fn zero() -> BigUint { BigUint::new(~[]) } - fn zero() -> BigUint { BigUint::new(~[]) } - - - fn is_zero(&self) -> bool { self.data.is_empty() } + pub fn is_zero(&self) -> bool { self.data.is_empty() } } impl One for BigUint { - - fn one() -> BigUint { BigUint::new(~[1]) } + pub fn one() -> BigUint { BigUint::new(~[1]) } } impl Unsigned for BigUint {} impl Add for BigUint { - fn add(&self, other: &BigUint) -> BigUint { - let new_len = uint::max(self.data.len(), other.data.len()); + let new_len = self.data.len().max(&other.data.len()); let mut carry = 0; let sum = do vec::from_fn(new_len) |i| { @@ -217,15 +203,17 @@ impl Add for BigUint { carry = hi; lo }; - if carry == 0 { return BigUint::new(sum) }; - return BigUint::new(sum + [carry]); + if carry == 0 { + BigUint::new(sum) + } else { + BigUint::new(sum + [carry]) + } } } impl Sub for BigUint { - fn sub(&self, other: &BigUint) -> BigUint { - let new_len = uint::max(self.data.len(), other.data.len()); + let new_len = self.data.len().max(&other.data.len()); let mut borrow = 0; let diff = do vec::from_fn(new_len) |i| { @@ -244,7 +232,8 @@ impl Sub for BigUint { }; assert_eq!(borrow, 0); // <=> assert!((self >= other)); - return BigUint::new(diff); + + BigUint::new(diff) } } @@ -261,7 +250,7 @@ impl Mul for BigUint { // = a1*b1 * base^2 + // (a1*b1 + a0*b0 - (a1-b0)*(b1-a0)) * base + // a0*b0 - let half_len = uint::max(s_len, o_len) / 2; + let half_len = s_len.max(&o_len) / 2; let (sHi, sLo) = cut_at(self, half_len); let (oHi, oLo) = cut_at(other, half_len); @@ -279,32 +268,31 @@ impl Mul for BigUint { return ll + mm.shl_unit(half_len) + hh.shl_unit(half_len * 2); - fn mul_digit(a: &BigUint, n: BigDigit) -> BigUint { if n == 0 { return Zero::zero(); } - if n == 1 { return copy *a; } + if n == 1 { return a.clone(); } let mut carry = 0; - let prod = do vec::map(a.data) |ai| { + let prod = do a.data.map |ai| { let (hi, lo) = BigDigit::from_uint( (*ai as uint) * (n as uint) + (carry as uint) ); carry = hi; lo }; - if carry == 0 { return BigUint::new(prod) }; - return BigUint::new(prod + [carry]); + if carry == 0 { + BigUint::new(prod) + } else { + BigUint::new(prod + [carry]) + } } - fn cut_at(a: &BigUint, n: uint) -> (BigUint, BigUint) { - let mid = uint::min(a.data.len(), n); - return (BigUint::from_slice(vec::slice(a.data, mid, - a.data.len())), - BigUint::from_slice(vec::slice(a.data, 0, mid))); + let mid = a.data.len().min(&n); + return (BigUint::from_slice(a.data.slice(mid, a.data.len())), + BigUint::from_slice(a.data.slice(0, mid))); } - fn sub_sign(a: BigUint, b: BigUint) -> (Ordering, BigUint) { match a.cmp(&b) { Less => (Less, b - a), @@ -316,52 +304,41 @@ impl Mul for BigUint { } impl Div for BigUint { - fn div(&self, other: &BigUint) -> BigUint { - let (q, _) = self.div_rem(other); - return q; + match self.div_rem(other) { (q, _) => q } } } impl Rem for BigUint { - fn rem(&self, other: &BigUint) -> BigUint { - let (_, r) = self.div_rem(other); - return r; + match self.div_rem(other) { (_, r) => r } } } impl Neg for BigUint { - fn neg(&self) -> BigUint { fail!() } } impl Integer for BigUint { - - fn div_rem(&self, other: &BigUint) -> (BigUint, BigUint) { + pub fn div_rem(&self, other: &BigUint) -> (BigUint, BigUint) { self.div_mod_floor(other) } - - fn div_floor(&self, other: &BigUint) -> BigUint { - let (d, _) = self.div_mod_floor(other); - return d; + pub fn div_floor(&self, other: &BigUint) -> BigUint { + match self.div_mod_floor(other) { (d, _) => d } } - - fn mod_floor(&self, other: &BigUint) -> BigUint { - let (_, m) = self.div_mod_floor(other); - return m; + pub fn mod_floor(&self, other: &BigUint) -> BigUint { + match self.div_mod_floor(other) { (_, m) => m } } - - fn div_mod_floor(&self, other: &BigUint) -> (BigUint, BigUint) { + pub fn div_mod_floor(&self, other: &BigUint) -> (BigUint, BigUint) { if other.is_zero() { fail!() } if self.is_zero() { return (Zero::zero(), Zero::zero()); } - if *other == One::one() { return (copy *self, Zero::zero()); } + if *other == One::one() { return (self.clone(), Zero::zero()); } match self.cmp(other) { - Less => return (Zero::zero(), copy *self), + Less => return (Zero::zero(), self.clone()), Equal => return (One::one(), Zero::zero()), Greater => {} // Do nothing } @@ -407,14 +384,13 @@ impl Integer for BigUint { return (d, m); } - fn div_estimate(a: &BigUint, b: &BigUint, n: uint) -> (BigUint, BigUint, BigUint) { if a.data.len() < n { - return (Zero::zero(), Zero::zero(), copy *a); + return (Zero::zero(), Zero::zero(), a.clone()); } - let an = vec::slice(a.data, a.data.len() - n, a.data.len()); + let an = a.data.slice(a.data.len() - n, a.data.len()); let bn = *b.data.last(); let mut d = ~[]; let mut carry = 0; @@ -428,7 +404,7 @@ impl Integer for BigUint { let shift = (a.data.len() - an.len()) - (b.data.len() - 1); if shift == 0 { - return (BigUint::new(d), One::one(), copy *b); + return (BigUint::new(d), One::one(), b.clone()); } return (BigUint::from_slice(d).shl_unit(shift), One::one::().shl_unit(shift), @@ -441,10 +417,9 @@ impl Integer for BigUint { * * The result is always positive */ - - fn gcd(&self, other: &BigUint) -> BigUint { + pub fn gcd(&self, other: &BigUint) -> BigUint { // Use Euclid's algorithm - let mut (m, n) = (copy *self, copy *other); + let mut (m, n) = (self.clone(), other.clone()); while !m.is_zero() { let temp = m; m = n % temp; @@ -456,16 +431,13 @@ impl Integer for BigUint { /** * Calculates the Lowest Common Multiple (LCM) of the number and `other` */ - - fn lcm(&self, other: &BigUint) -> BigUint { ((*self * *other) / self.gcd(other)) } + pub fn lcm(&self, other: &BigUint) -> BigUint { ((*self * *other) / self.gcd(other)) } /// Returns `true` if the number can be divided by `other` without leaving a remainder - - fn is_multiple_of(&self, other: &BigUint) -> bool { (*self % *other).is_zero() } + pub fn is_multiple_of(&self, other: &BigUint) -> bool { (*self % *other).is_zero() } /// Returns `true` if the number is divisible by `2` - - fn is_even(&self) -> bool { + pub fn is_even(&self) -> bool { // Considering only the last digit. if self.data.is_empty() { true @@ -475,32 +447,27 @@ impl Integer for BigUint { } /// Returns `true` if the number is not divisible by `2` - - fn is_odd(&self) -> bool { !self.is_even() } + pub fn is_odd(&self) -> bool { !self.is_even() } } impl IntConvertible for BigUint { - - fn to_int(&self) -> int { - uint::min(self.to_uint(), int::max_value as uint) as int + pub fn to_int(&self) -> int { + self.to_uint().min(&(Bounded::max_value::() as uint)) as int } - - fn from_int(n: int) -> BigUint { + pub fn from_int(n: int) -> BigUint { if (n < 0) { Zero::zero() } else { BigUint::from_uint(n as uint) } } } impl ToStrRadix for BigUint { - - fn to_str_radix(&self, radix: uint) -> ~str { + pub fn to_str_radix(&self, radix: uint) -> ~str { assert!(1 < radix && radix <= 16); let (base, max_len) = get_radix_base(radix); if base == BigDigit::base { return fill_concat(self.data, radix, max_len) } - return fill_concat(convert_base(copy *self, base), radix, max_len); - + return fill_concat(convert_base(self.clone(), base), radix, max_len); fn convert_base(n: BigUint, base: uint) -> ~[BigDigit] { let divider = BigUint::from_uint(base); @@ -517,60 +484,55 @@ impl ToStrRadix for BigUint { return result; } - fn fill_concat(v: &[BigDigit], radix: uint, l: uint) -> ~str { if v.is_empty() { return ~"0" } - let s = str::concat(vec::reversed(v).map(|n| { + let s = vec::reversed(v).map(|n| { let s = uint::to_str_radix(*n as uint, radix); str::from_chars(vec::from_elem(l - s.len(), '0')) + s - })); - str::trim_left_chars(s, ['0']).to_owned() + }).concat(); + s.trim_left_chars(['0']).to_owned() } } } impl FromStrRadix for BigUint { /// Creates and initializes an BigUint. - - pub fn from_str_radix(s: &str, radix: uint) - -> Option { - BigUint::parse_bytes(str::to_bytes(s), radix) + pub fn from_str_radix(s: &str, radix: uint) -> Option { + BigUint::parse_bytes(s.to_bytes(), radix) } } impl BigUint { /// Creates and initializes an BigUint. - pub fn new(v: ~[BigDigit]) -> BigUint { // omit trailing zeros let new_len = v.rposition(|n| *n != 0).map_default(0, |p| *p + 1); - if new_len == v.len() { return BigUint { data: v }; } - let mut v = v; - v.truncate(new_len); - return BigUint { data: v }; + if new_len == v.len() { + BigUint { data: v } + } else { + let mut v = v; + v.truncate(new_len); + BigUint { data: v } + } } /// Creates and initializes an BigUint. - pub fn from_uint(n: uint) -> BigUint { match BigDigit::from_uint(n) { (0, 0) => Zero::zero(), (0, n0) => BigUint::new(~[n0]), - (n1, n0) => BigUint::new(~[n0, n1]) + (n1, n0) => BigUint::new(~[n0, n1]), } } /// Creates and initializes an BigUint. - pub fn from_slice(slice: &[BigDigit]) -> BigUint { - return BigUint::new(vec::to_owned(slice)); + BigUint::new(slice.to_owned()) } /// Creates and initializes an BigUint. - - pub fn parse_bytes(buf: &[u8], radix: uint) - -> Option { + pub fn parse_bytes(buf: &[u8], radix: uint) -> Option { let (base, unit_len) = get_radix_base(radix); let base_num: BigUint = BigUint::from_uint(base); @@ -578,12 +540,12 @@ impl BigUint { let mut n: BigUint = Zero::zero(); let mut power: BigUint = One::one(); loop { - let start = uint::max(end, unit_len) - unit_len; - match uint::parse_bytes(vec::slice(buf, start, end), radix) { + let start = end.max(&unit_len) - unit_len; + match uint::parse_bytes(buf.slice(start, end), radix) { // FIXME(#6102): Assignment operator for BigInt causes ICE // Some(d) => n += BigUint::from_uint(d) * power, Some(d) => n = n + BigUint::from_uint(d) * power, - None => return None + None => return None, } if end <= unit_len { return Some(n); @@ -595,53 +557,56 @@ impl BigUint { } } - - /// Converts this big integer into a uint, returning the uint::max_value if - /// it's too large to fit in a uint. + /// Converts this big integer into a uint, returning the `Bounded::max_value::()` + /// if it's too large to fit in a uint. pub fn to_uint(&self) -> uint { match self.data.len() { 0 => 0, 1 => self.data[0] as uint, 2 => BigDigit::to_uint(self.data[1], self.data[0]), - _ => uint::max_value + _ => Bounded::max_value::(), } } - priv fn shl_unit(&self, n_unit: uint) -> BigUint { - if n_unit == 0 || self.is_zero() { return copy *self; } - - return BigUint::new(vec::from_elem(n_unit, 0) + self.data); + if n_unit == 0 || self.is_zero() { + self.clone() + } else { + BigUint::new(vec::from_elem(n_unit, 0) + self.data) + } } - priv fn shl_bits(&self, n_bits: uint) -> BigUint { - if n_bits == 0 || self.is_zero() { return copy *self; } + if n_bits == 0 || self.is_zero() { return self.clone(); } let mut carry = 0; - let shifted = do vec::map(self.data) |elem| { + let shifted = do self.data.map |elem| { let (hi, lo) = BigDigit::from_uint( (*elem as uint) << n_bits | (carry as uint) ); carry = hi; lo }; - if carry == 0 { return BigUint::new(shifted); } - return BigUint::new(shifted + [carry]); + if carry == 0 { + BigUint::new(shifted) + } else { + BigUint::new(shifted + [carry]) + } } - priv fn shr_unit(&self, n_unit: uint) -> BigUint { - if n_unit == 0 { return copy *self; } - if self.data.len() < n_unit { return Zero::zero(); } - return BigUint::from_slice( - vec::slice(self.data, n_unit, self.data.len()) - ); + if n_unit == 0 { + self.clone() + } else if self.data.len() < n_unit { + Zero::zero() + } else { + BigUint::from_slice(self.data.slice(n_unit, self.data.len())) + } } priv fn shr_bits(&self, n_bits: uint) -> BigUint { - if n_bits == 0 || self.data.is_empty() { return copy *self; } + if n_bits == 0 || self.data.is_empty() { return self.clone(); } let mut borrow = 0; let mut shifted = ~[]; @@ -649,12 +614,12 @@ impl BigUint { shifted = ~[(*elem >> n_bits) | borrow] + shifted; borrow = *elem << (BigDigit::bits - n_bits); } - return BigUint::new(shifted); + + BigUint::new(shifted) } } #[cfg(target_arch = "x86_64")] - priv fn get_radix_base(radix: uint) -> (uint, uint) { assert!(1 < radix && radix <= 16); match radix { @@ -673,14 +638,13 @@ priv fn get_radix_base(radix: uint) -> (uint, uint) { 14 => (1475789056, 8), 15 => (2562890625, 8), 16 => (4294967296, 8), - _ => fail!() + _ => fail!(), } } #[cfg(target_arch = "arm")] #[cfg(target_arch = "x86")] #[cfg(target_arch = "mips")] - priv fn get_radix_base(radix: uint) -> (uint, uint) { assert!(1 < radix && radix <= 16); match radix { @@ -699,7 +663,7 @@ priv fn get_radix_base(radix: uint) -> (uint, uint) { 14 => (38416, 4), 15 => (50625, 4), 16 => (65536, 4), - _ => fail!() + _ => fail!(), } } @@ -708,7 +672,6 @@ priv fn get_radix_base(radix: uint) -> (uint, uint) { pub enum Sign { Minus, Zero, Plus } impl Ord for Sign { - fn lt(&self, other: &Sign) -> bool { match self.cmp(other) { Less => true, _ => false} } @@ -727,24 +690,22 @@ impl Ord for Sign { } impl TotalOrd for Sign { - fn cmp(&self, other: &Sign) -> Ordering { match (*self, *other) { (Minus, Minus) | (Zero, Zero) | (Plus, Plus) => Equal, (Minus, Zero) | (Minus, Plus) | (Zero, Plus) => Less, - _ => Greater + _ => Greater, } } } impl Neg for Sign { /// Negate Sign value. - fn neg(&self) -> Sign { match *self { Minus => Plus, Zero => Zero, - Plus => Minus + Plus => Minus, } } } @@ -757,21 +718,18 @@ pub struct BigInt { } impl Eq for BigInt { - fn eq(&self, other: &BigInt) -> bool { self.equals(other) } fn ne(&self, other: &BigInt) -> bool { !self.equals(other) } } impl TotalEq for BigInt { - fn equals(&self, other: &BigInt) -> bool { match self.cmp(other) { Equal => true, _ => false } } } impl Ord for BigInt { - fn lt(&self, other: &BigInt) -> bool { match self.cmp(other) { Less => true, _ => false} } @@ -790,7 +748,6 @@ impl Ord for BigInt { } impl TotalOrd for BigInt { - fn cmp(&self, other: &BigInt) -> Ordering { let scmp = self.sign.cmp(&other.sign); if scmp != Equal { return scmp; } @@ -804,12 +761,10 @@ impl TotalOrd for BigInt { } impl ToStr for BigInt { - fn to_str(&self) -> ~str { self.to_str_radix(10) } } impl FromStr for BigInt { - fn from_str(s: &str) -> Option { FromStrRadix::from_str_radix(s, 10) } @@ -818,70 +773,62 @@ impl FromStr for BigInt { impl Num for BigInt {} impl Orderable for BigInt { - - fn min(&self, other: &BigInt) -> BigInt { + pub fn min(&self, other: &BigInt) -> BigInt { if self < other { self.clone() } else { other.clone() } } - - fn max(&self, other: &BigInt) -> BigInt { + pub fn max(&self, other: &BigInt) -> BigInt { if self > other { self.clone() } else { other.clone() } } - - fn clamp(&self, mn: &BigInt, mx: &BigInt) -> BigInt { - if self > mx { mx.clone() } else - if self < mn { mn.clone() } else { self.clone() } + pub fn clamp(&self, mn: &BigInt, mx: &BigInt) -> BigInt { + cond!( + (self > mx) { mx.clone() } + (self < mn) { mn.clone() } + _ { self.clone() } + ) } } impl Shl for BigInt { - fn shl(&self, rhs: &uint) -> BigInt { BigInt::from_biguint(self.sign, self.data << *rhs) } } impl Shr for BigInt { - fn shr(&self, rhs: &uint) -> BigInt { BigInt::from_biguint(self.sign, self.data >> *rhs) } } impl Zero for BigInt { - - fn zero() -> BigInt { + pub fn zero() -> BigInt { BigInt::from_biguint(Zero, Zero::zero()) } - - fn is_zero(&self) -> bool { self.sign == Zero } + pub fn is_zero(&self) -> bool { self.sign == Zero } } impl One for BigInt { - - fn one() -> BigInt { + pub fn one() -> BigInt { BigInt::from_biguint(Plus, One::one()) } } impl Signed for BigInt { - - fn abs(&self) -> BigInt { + pub fn abs(&self) -> BigInt { match self.sign { Plus | Zero => self.clone(), Minus => BigInt::from_biguint(Plus, self.data.clone()) } } - - fn abs_sub(&self, other: &BigInt) -> BigInt { + pub fn abs_sub(&self, other: &BigInt) -> BigInt { if *self <= *other { Zero::zero() } else { *self - *other } } - - fn signum(&self) -> BigInt { + pub fn signum(&self) -> BigInt { match self.sign { Plus => BigInt::from_biguint(Plus, One::one()), Minus => BigInt::from_biguint(Minus, One::one()), @@ -889,21 +836,17 @@ impl Signed for BigInt { } } + pub fn is_positive(&self) -> bool { self.sign == Plus } - fn is_positive(&self) -> bool { self.sign == Plus } - - - fn is_negative(&self) -> bool { self.sign == Minus } + pub fn is_negative(&self) -> bool { self.sign == Minus } } impl Add for BigInt { - fn add(&self, other: &BigInt) -> BigInt { match (self.sign, other.sign) { (Zero, _) => other.clone(), (_, Zero) => self.clone(), - (Plus, Plus) => BigInt::from_biguint(Plus, - self.data + other.data), + (Plus, Plus) => BigInt::from_biguint(Plus, self.data + other.data), (Plus, Minus) => self - (-*other), (Minus, Plus) => other - (-*self), (Minus, Minus) => -((-self) + (-*other)) @@ -912,7 +855,6 @@ impl Add for BigInt { } impl Sub for BigInt { - fn sub(&self, other: &BigInt) -> BigInt { match (self.sign, other.sign) { (Zero, _) => -other, @@ -930,7 +872,6 @@ impl Sub for BigInt { } impl Mul for BigInt { - fn mul(&self, other: &BigInt) -> BigInt { match (self.sign, other.sign) { (Zero, _) | (_, Zero) => Zero::zero(), @@ -945,31 +886,25 @@ impl Mul for BigInt { } impl Div for BigInt { - fn div(&self, other: &BigInt) -> BigInt { - let (q, _) = self.div_rem(other); - return q; + match self.div_rem(other) { (q, _) => q } } } impl Rem for BigInt { - fn rem(&self, other: &BigInt) -> BigInt { - let (_, r) = self.div_rem(other); - return r; + match self.div_rem(other) { (_, r) => r } } } impl Neg for BigInt { - fn neg(&self) -> BigInt { BigInt::from_biguint(self.sign.neg(), self.data.clone()) } } impl Integer for BigInt { - - fn div_rem(&self, other: &BigInt) -> (BigInt, BigInt) { + pub fn div_rem(&self, other: &BigInt) -> (BigInt, BigInt) { // r.sign == self.sign let (d_ui, r_ui) = self.data.div_mod_floor(&other.data); let d = BigInt::from_biguint(Plus, d_ui); @@ -979,24 +914,19 @@ impl Integer for BigInt { (Plus, Plus) | (Zero, Plus) => ( d, r), (Plus, Minus) | (Zero, Minus) => (-d, r), (Minus, Plus) => (-d, -r), - (Minus, Minus) => ( d, -r) + (Minus, Minus) => ( d, -r), } } - - fn div_floor(&self, other: &BigInt) -> BigInt { - let (d, _) = self.div_mod_floor(other); - return d; + pub fn div_floor(&self, other: &BigInt) -> BigInt { + match self.div_mod_floor(other) { (d, _) => d } } - - fn mod_floor(&self, other: &BigInt) -> BigInt { - let (_, m) = self.div_mod_floor(other); - return m; + pub fn mod_floor(&self, other: &BigInt) -> BigInt { + match self.div_mod_floor(other) { (_, m) => m } } - - fn div_mod_floor(&self, other: &BigInt) -> (BigInt, BigInt) { + pub fn div_mod_floor(&self, other: &BigInt) -> (BigInt, BigInt) { // m.sign == other.sign let (d_ui, m_ui) = self.data.div_rem(&other.data); let d = BigInt::from_biguint(Plus, d_ui); @@ -1014,7 +944,7 @@ impl Integer for BigInt { } else { (-d - One::one(), other - m) }, - (Minus, Minus) => (d, -m) + (Minus, Minus) => (d, -m), } } @@ -1023,74 +953,63 @@ impl Integer for BigInt { * * The result is always positive */ - - fn gcd(&self, other: &BigInt) -> BigInt { + pub fn gcd(&self, other: &BigInt) -> BigInt { BigInt::from_biguint(Plus, self.data.gcd(&other.data)) } /** * Calculates the Lowest Common Multiple (LCM) of the number and `other` */ - - fn lcm(&self, other: &BigInt) -> BigInt { + pub fn lcm(&self, other: &BigInt) -> BigInt { BigInt::from_biguint(Plus, self.data.lcm(&other.data)) } /// Returns `true` if the number can be divided by `other` without leaving a remainder - - fn is_multiple_of(&self, other: &BigInt) -> bool { self.data.is_multiple_of(&other.data) } + pub fn is_multiple_of(&self, other: &BigInt) -> bool { self.data.is_multiple_of(&other.data) } /// Returns `true` if the number is divisible by `2` - - fn is_even(&self) -> bool { self.data.is_even() } + pub fn is_even(&self) -> bool { self.data.is_even() } /// Returns `true` if the number is not divisible by `2` - - fn is_odd(&self) -> bool { self.data.is_odd() } + pub fn is_odd(&self) -> bool { self.data.is_odd() } } impl IntConvertible for BigInt { - - fn to_int(&self) -> int { + pub fn to_int(&self) -> int { match self.sign { - Plus => uint::min(self.to_uint(), int::max_value as uint) as int, + Plus => self.to_uint().min(&(Bounded::max_value::() as uint)) as int, Zero => 0, - Minus => uint::min((-self).to_uint(), - (int::max_value as uint) + 1) as int + Minus => (-self).to_uint().min(&((Bounded::max_value::() as uint) + 1)) as int } } - - fn from_int(n: int) -> BigInt { + pub fn from_int(n: int) -> BigInt { if n > 0 { - return BigInt::from_biguint(Plus, BigUint::from_uint(n as uint)); - } - if n < 0 { - return BigInt::from_biguint( - Minus, BigUint::from_uint(uint::max_value - (n as uint) + 1) - ); + BigInt::from_biguint(Plus, BigUint::from_uint(n as uint)) + } else if n < 0 { + BigInt::from_biguint( + Minus, BigUint::from_uint(Bounded::max_value::() - (n as uint) + 1) + ) + } else { + Zero::zero() } - return Zero::zero(); } } impl ToStrRadix for BigInt { - - fn to_str_radix(&self, radix: uint) -> ~str { + pub fn to_str_radix(&self, radix: uint) -> ~str { match self.sign { Plus => self.data.to_str_radix(radix), Zero => ~"0", - Minus => ~"-" + self.data.to_str_radix(radix) + Minus => ~"-" + self.data.to_str_radix(radix), } } } impl FromStrRadix for BigInt { /// Creates and initializes an BigInt. - - fn from_str_radix(s: &str, radix: uint) - -> Option { - BigInt::parse_bytes(str::to_bytes(s), radix) + pub fn from_str_radix(s: &str, radix: uint) -> Option { + BigInt::parse_bytes(s.to_bytes(), radix) } } @@ -1101,31 +1020,31 @@ impl BigInt { } /// Creates and initializes an BigInt. - pub fn from_biguint(sign: Sign, data: BigUint) -> BigInt { if sign == Zero || data.is_zero() { - return BigInt { sign: Zero, data: Zero::zero() }; + BigInt { sign: Zero, data: Zero::zero() } + } else { + BigInt { sign: sign, data: data } } - return BigInt { sign: sign, data: data }; } /// Creates and initializes an BigInt. - pub fn from_uint(n: uint) -> BigInt { - if n == 0 { return Zero::zero(); } - return BigInt::from_biguint(Plus, BigUint::from_uint(n)); + if n == 0 { + Zero::zero() + } else { + BigInt::from_biguint(Plus, BigUint::from_uint(n)) + } } /// Creates and initializes an BigInt. - pub fn from_slice(sign: Sign, slice: &[BigDigit]) -> BigInt { BigInt::from_biguint(sign, BigUint::from_slice(slice)) } /// Creates and initializes an BigInt. - pub fn parse_bytes(buf: &[u8], radix: uint) - -> Option { + pub fn parse_bytes(buf: &[u8], radix: uint) -> Option { if buf.is_empty() { return None; } let mut sign = Plus; let mut start = 0; @@ -1133,15 +1052,15 @@ impl BigInt { sign = Minus; start = 1; } - return BigUint::parse_bytes(vec::slice(buf, start, buf.len()), radix) - .map_consume(|bu| BigInt::from_biguint(sign, bu)); + BigUint::parse_bytes(buf.slice(start, buf.len()), radix) + .map_consume(|bu| BigInt::from_biguint(sign, bu)) } pub fn to_uint(&self) -> uint { match self.sign { Plus => self.data.to_uint(), Zero => 0, - Minus => 0 + Minus => 0, } } } @@ -1177,7 +1096,7 @@ mod biguint_tests { let data = [ &[], &[1], &[2], &[-1], &[0, 1], &[2, 1], &[1, 1, 1] ] .map(|v| BigUint::from_slice(*v)); for data.eachi |i, ni| { - for vec::slice(data, i, data.len()).eachi |j0, nj| { + for data.slice(i, data.len()).eachi |j0, nj| { let j = j0 + i; if i == j { assert_eq!(ni.cmp(nj), Equal); @@ -1306,13 +1225,13 @@ mod biguint_tests { check(~[], 0); check(~[1], 1); - check(~[-1], (uint::max_value >> BigDigit::bits) as int); - check(~[ 0, 1], ((uint::max_value >> BigDigit::bits) + 1) as int); - check(~[-1, -1 >> 1], int::max_value); + check(~[-1], (Bounded::max_value::() >> BigDigit::bits) as int); + check(~[ 0, 1], ((Bounded::max_value::() >> BigDigit::bits) + 1) as int); + check(~[-1, -1 >> 1], Bounded::max_value::()); - assert_eq!(BigUint::new(~[0, -1]).to_int(), int::max_value); - assert_eq!(BigUint::new(~[0, 0, 1]).to_int(), int::max_value); - assert_eq!(BigUint::new(~[0, 0, -1]).to_int(), int::max_value); + assert_eq!(BigUint::new(~[0, -1]).to_int(), Bounded::max_value::()); + assert_eq!(BigUint::new(~[0, 0, 1]).to_int(), Bounded::max_value::()); + assert_eq!(BigUint::new(~[0, 0, -1]).to_int(), Bounded::max_value::()); } #[test] @@ -1325,13 +1244,13 @@ mod biguint_tests { check(~[], 0); check(~[ 1], 1); - check(~[-1], uint::max_value >> BigDigit::bits); - check(~[ 0, 1], (uint::max_value >> BigDigit::bits) + 1); - check(~[ 0, -1], uint::max_value << BigDigit::bits); - check(~[-1, -1], uint::max_value); + check(~[-1], Bounded::max_value::() >> BigDigit::bits); + check(~[ 0, 1], (Bounded::max_value::() >> BigDigit::bits) + 1); + check(~[ 0, -1], Bounded::max_value::() << BigDigit::bits); + check(~[-1, -1], Bounded::max_value::()); - assert_eq!(BigUint::new(~[0, 0, 1]).to_uint(), uint::max_value); - assert_eq!(BigUint::new(~[0, 0, -1]).to_uint(), uint::max_value); + assert_eq!(BigUint::new(~[0, 0, 1]).to_uint(), Bounded::max_value::()); + assert_eq!(BigUint::new(~[0, 0, -1]).to_uint(), Bounded::max_value::()); } static sum_triples: &'static [(&'static [BigDigit], @@ -1653,7 +1572,7 @@ mod bigint_tests { nums.push_all_move(vs.map(|s| BigInt::from_slice(Plus, *s))); for nums.eachi |i, ni| { - for vec::slice(nums, i, nums.len()).eachi |j0, nj| { + for nums.slice(i, nums.len()).eachi |j0, nj| { let j = i + j0; if i == j { assert_eq!(ni.cmp(nj), Equal); @@ -1695,25 +1614,25 @@ mod bigint_tests { check(Zero::zero(), 0); check(One::one(), 1); check(BigInt::from_biguint( - Plus, BigUint::from_uint(int::max_value as uint) - ), int::max_value); + Plus, BigUint::from_uint(Bounded::max_value::() as uint) + ), Bounded::max_value::()); assert!(BigInt::from_biguint( - Plus, BigUint::from_uint(int::max_value as uint + 1) - ).to_int() == int::max_value); + Plus, BigUint::from_uint(Bounded::max_value::() as uint + 1) + ).to_int() == Bounded::max_value::()); assert!(BigInt::from_biguint( Plus, BigUint::new(~[1, 2, 3]) - ).to_int() == int::max_value); + ).to_int() == Bounded::max_value::()); check(BigInt::from_biguint( - Minus, BigUint::from_uint(-int::min_value as uint) - ), int::min_value); + Minus, BigUint::from_uint(-Bounded::min_value::() as uint) + ), Bounded::min_value::()); assert!(BigInt::from_biguint( - Minus, BigUint::from_uint(-int::min_value as uint + 1) - ).to_int() == int::min_value); + Minus, BigUint::from_uint(-Bounded::min_value::() as uint + 1) + ).to_int() == Bounded::min_value::()); assert!(BigInt::from_biguint( Minus, BigUint::new(~[1, 2, 3]) - ).to_int() == int::min_value); + ).to_int() == Bounded::min_value::()); } #[test] @@ -1727,14 +1646,14 @@ mod bigint_tests { check(One::one(), 1); check( - BigInt::from_biguint(Plus, BigUint::from_uint(uint::max_value)), - uint::max_value); + BigInt::from_biguint(Plus, BigUint::from_uint(Bounded::max_value::())), + Bounded::max_value::()); assert!(BigInt::from_biguint( Plus, BigUint::new(~[1, 2, 3]) - ).to_uint() == uint::max_value); + ).to_uint() == Bounded::max_value::()); assert!(BigInt::from_biguint( - Minus, BigUint::from_uint(uint::max_value) + Minus, BigUint::from_uint(Bounded::max_value::()) ).to_uint() == 0); assert!(BigInt::from_biguint( Minus, BigUint::new(~[1, 2, 3]) @@ -2030,10 +1949,8 @@ mod bigint_tests { #[test] fn test_neg() { - assert!(-BigInt::new(Plus, ~[1, 1, 1]) == - BigInt::new(Minus, ~[1, 1, 1])); - assert!(-BigInt::new(Minus, ~[1, 1, 1]) == - BigInt::new(Plus, ~[1, 1, 1])); + assert!(-BigInt::new(Plus, ~[1, 1, 1]) == BigInt::new(Minus, ~[1, 1, 1])); + assert!(-BigInt::new(Minus, ~[1, 1, 1]) == BigInt::new(Plus, ~[1, 1, 1])); assert_eq!(-Zero::zero::(), Zero::zero::()); } } diff --git a/src/libextra/num/complex.rs b/src/libextra/num/complex.rs index 10bfe9409daa4..38eea8f64eb00 100644 --- a/src/libextra/num/complex.rs +++ b/src/libextra/num/complex.rs @@ -125,19 +125,19 @@ impl Neg> for Cmplx { /* constants */ impl Zero for Cmplx { #[inline] - fn zero() -> Cmplx { + pub fn zero() -> Cmplx { Cmplx::new(Zero::zero(), Zero::zero()) } #[inline] - fn is_zero(&self) -> bool { + pub fn is_zero(&self) -> bool { *self == Zero::zero() } } impl One for Cmplx { #[inline] - fn one() -> Cmplx { + pub fn one() -> Cmplx { Cmplx::new(One::one(), Zero::zero()) } } @@ -154,7 +154,7 @@ impl ToStr for Cmplx { } impl ToStrRadix for Cmplx { - fn to_str_radix(&self, radix: uint) -> ~str { + pub fn to_str_radix(&self, radix: uint) -> ~str { if self.im < Zero::zero() { fmt!("%s-%si", self.re.to_str_radix(radix), (-self.im).to_str_radix(radix)) } else { diff --git a/src/libextra/num/rational.rs b/src/libextra/num/rational.rs index 1a8ab75b3dd0d..70897f64e007f 100644 --- a/src/libextra/num/rational.rs +++ b/src/libextra/num/rational.rs @@ -167,12 +167,12 @@ impl impl Zero for Ratio { #[inline] - fn zero() -> Ratio { + pub fn zero() -> Ratio { Ratio::new_raw(Zero::zero(), One::one()) } #[inline] - fn is_zero(&self) -> bool { + pub fn is_zero(&self) -> bool { *self == Zero::zero() } } @@ -180,7 +180,7 @@ impl impl One for Ratio { #[inline] - fn one() -> Ratio { + pub fn one() -> Ratio { Ratio::new_raw(One::one(), One::one()) } } @@ -192,7 +192,7 @@ impl impl Round for Ratio { - fn floor(&self) -> Ratio { + pub fn floor(&self) -> Ratio { if *self < Zero::zero() { Ratio::from_integer((self.numer - self.denom + One::one()) / self.denom) } else { @@ -200,7 +200,7 @@ impl } } - fn ceil(&self) -> Ratio { + pub fn ceil(&self) -> Ratio { if *self < Zero::zero() { Ratio::from_integer(self.numer / self.denom) } else { @@ -209,7 +209,7 @@ impl } #[inline(always)] - fn round(&self) -> Ratio { + pub fn round(&self) -> Ratio { if *self < Zero::zero() { Ratio::from_integer((self.numer - self.denom + One::one()) / self.denom) } else { @@ -218,18 +218,18 @@ impl } #[inline(always)] - fn trunc(&self) -> Ratio { + pub fn trunc(&self) -> Ratio { Ratio::from_integer(self.numer / self.denom) } - fn fract(&self) -> Ratio { + pub fn fract(&self) -> Ratio { Ratio::new_raw(self.numer % self.denom, self.denom.clone()) } } impl Fractional for Ratio { #[inline] - fn recip(&self) -> Ratio { + pub fn recip(&self) -> Ratio { Ratio::new_raw(self.denom.clone(), self.numer.clone()) } } @@ -243,7 +243,7 @@ impl ToStr for Ratio { } impl ToStrRadix for Ratio { /// Renders as `numer/denom` where the numbers are in base `radix`. - fn to_str_radix(&self, radix: uint) -> ~str { + pub fn to_str_radix(&self, radix: uint) -> ~str { fmt!("%s/%s", self.numer.to_str_radix(radix), self.denom.to_str_radix(radix)) } } @@ -268,7 +268,7 @@ impl impl FromStrRadix for Ratio { /// Parses `numer/denom` where the numbers are in base `radix`. - fn from_str_radix(s: &str, radix: uint) -> Option> { + pub fn from_str_radix(s: &str, radix: uint) -> Option> { let split = vec::build(|push| { for str::each_splitn_char(s, '/', 1) |s| { push(s.to_owned()); diff --git a/src/libextra/par.rs b/src/libextra/par.rs index 23b7cdc099747..9c1272842117b 100644 --- a/src/libextra/par.rs +++ b/src/libextra/par.rs @@ -14,7 +14,6 @@ use core::iterator::IteratorUtil; use core::cast; use core::ptr; use core::sys; -use core::uint; use core::vec; use future_spawn = future::spawn; @@ -46,7 +45,7 @@ fn map_slices( ~[f()(0u, xs)] } else { - let num_tasks = uint::min(max_tasks, len / min_granularity); + let num_tasks = max_tasks.min(&(len / min_granularity)); let items_per_task = len / num_tasks; @@ -54,7 +53,7 @@ fn map_slices( let mut base = 0u; info!("spawning tasks"); while base < len { - let end = uint::min(len, base + items_per_task); + let end = len.min(&(base + items_per_task)); do vec::as_imm_buf(xs) |p, _len| { let f = f(); let base = base; diff --git a/src/libextra/rope.rs b/src/libextra/rope.rs index 413a498a20ec5..db6edfd988364 100644 --- a/src/libextra/rope.rs +++ b/src/libextra/rope.rs @@ -1044,7 +1044,7 @@ pub mod node { right: right, char_len: char_len(left) + char_len(right), byte_len: byte_len(left) + byte_len(right), - height: uint::max(height(left), height(right)) + 1u, + height: height(left).max(&height(right)) + 1u, }) } diff --git a/src/libextra/stats.rs b/src/libextra/stats.rs index 0cc1ee9a1d716..c6b674525e3e0 100644 --- a/src/libextra/stats.rs +++ b/src/libextra/stats.rs @@ -14,9 +14,6 @@ use core::prelude::*; use core::iterator::*; use core::vec; -use core::f64; -use core::cmp; -use core::num; use sort; // NB: this can probably be rewritten in terms of num::Num @@ -42,12 +39,12 @@ impl<'self> Stats for &'self [f64] { fn min(self) -> f64 { assert!(self.len() != 0); - self.iter().fold(self[0], |p,q| cmp::min(p, *q)) + self.iter().fold(self[0], |p,q| p.min(q)) } fn max(self) -> f64 { assert!(self.len() != 0); - self.iter().fold(self[0], |p,q| cmp::max(p, *q)) + self.iter().fold(self[0], |p,q| p.max(q)) } fn mean(self) -> f64 { @@ -82,7 +79,7 @@ impl<'self> Stats for &'self [f64] { } fn std_dev(self) -> f64 { - f64::sqrt(self.var()) + self.var().sqrt() } fn std_dev_pct(self) -> f64 { @@ -91,7 +88,7 @@ impl<'self> Stats for &'self [f64] { fn median_abs_dev(self) -> f64 { let med = self.median(); - let abs_devs = self.map(|v| num::abs(med - *v)); + let abs_devs = self.map(|v| (med - *v).abs()); abs_devs.median() } diff --git a/src/libextra/test.rs b/src/libextra/test.rs index 6a9751b66e01e..1088cec160bd9 100644 --- a/src/libextra/test.rs +++ b/src/libextra/test.rs @@ -613,7 +613,6 @@ fn calc_result(desc: &TestDesc, task_succeeded: bool) -> TestResult { pub mod bench { use core::prelude::*; - use core::num; use core::rand::RngUtil; use core::rand; use core::u64; @@ -699,7 +698,7 @@ pub mod bench { n = 1_000_000_000 / self.ns_per_iter(); } - n = u64::max(u64::min(n+n/2, 100*last), last+1); + n = (n + n / 2).min(&(100 * last)).max(&(last + 1)); n = round_up(n); self.bench_n(n, f); } @@ -729,7 +728,7 @@ pub mod bench { let med = samples.median(); let mad = samples.median_abs_dev(); let samples = do vec::filter(samples) |f| { - num::abs(*f - med) <= 3.0 * mad + (*f - med).abs() <= 3.0 * mad }; debug!("%u samples, median %f, MAD=%f, %u survived filter", @@ -741,7 +740,7 @@ pub mod bench { let curr_madp = samples.median_abs_dev_pct(); if self.ns_elapsed() > 1_000_000 && (curr_madp < 1.0 || - num::abs(curr_madp - prev_madp) < 0.1) { + (curr_madp - prev_madp).abs() < 0.1) { return samples; } prev_madp = curr_madp; diff --git a/src/libextra/time.rs b/src/libextra/time.rs index dd3e4f48c634b..b765976be5c63 100644 --- a/src/libextra/time.rs +++ b/src/libextra/time.rs @@ -12,7 +12,6 @@ use core::prelude::*; -use core::i32; use core::int; use core::io; use core::str; @@ -251,7 +250,7 @@ impl Tm { } else { let s = self.strftime("%Y-%m-%dT%H:%M:%S"); let sign = if self.tm_gmtoff > 0_i32 { '+' } else { '-' }; - let mut m = i32::abs(self.tm_gmtoff) / 60_i32; + let mut m = self.tm_gmtoff.abs() / 60_i32; let h = m / 60_i32; m -= h * 60_i32; s + fmt!("%c%02d:%02d", sign, h as int, m as int) @@ -834,7 +833,7 @@ priv fn do_strftime(format: &str, tm: &Tm) -> ~str { 'Z' => copy tm.tm_zone, 'z' => { let sign = if tm.tm_gmtoff > 0_i32 { '+' } else { '-' }; - let mut m = i32::abs(tm.tm_gmtoff) / 60_i32; + let mut m = tm.tm_gmtoff.abs() / 60_i32; let h = m / 60_i32; m -= h * 60_i32; fmt!("%c%02d%02d", sign, h as int, m as int) diff --git a/src/libextra/treemap.rs b/src/libextra/treemap.rs index 9db3d48a3b810..32fa10f75b237 100644 --- a/src/libextra/treemap.rs +++ b/src/libextra/treemap.rs @@ -15,7 +15,6 @@ use core::prelude::*; use core::iterator::*; -use core::uint; use core::util::{swap, replace}; // This is implemented as an AA tree, which is a simplified variation of @@ -59,13 +58,12 @@ impl Eq for TreeMap { } // Lexicographical comparison -fn lt(a: &TreeMap, - b: &TreeMap) -> bool { +fn lt(a: &TreeMap, b: &TreeMap) -> bool { let mut x = a.iter(); let mut y = b.iter(); let (a_len, b_len) = (a.len(), b.len()); - for uint::min(a_len, b_len).times { + for a_len.min(&b_len).times { let (key_a,_) = x.next().unwrap(); let (key_b,_) = y.next().unwrap(); if *key_a < *key_b { return true; } diff --git a/src/libfuzzer/fuzzer.rc b/src/libfuzzer/fuzzer.rc index c6410d16c7429..8a8e7bfd1c014 100644 --- a/src/libfuzzer/fuzzer.rc +++ b/src/libfuzzer/fuzzer.rc @@ -327,10 +327,10 @@ pub fn check_variants_T(crate: @ast::crate, let L = things.len(); if L < 100 { - do under(uint::min(L, 20)) |i| { + do under(L.min(&20)) |i| { error!("Replacing... #%?", uint::to_str(i)); let fname = str::to_owned(filename.to_str()); - do under(uint::min(L, 30)) |j| { + do under(L.min(&30)) |j| { let fname = fname.to_str(); error!("With... %?", stringifier(things[j], intr)); let crate2 = replacer(crate, i, things[j], cx.mode); diff --git a/src/librustc/back/rpath.rs b/src/librustc/back/rpath.rs index a84cb2cdbe10e..f972941ed34dc 100644 --- a/src/librustc/back/rpath.rs +++ b/src/librustc/back/rpath.rs @@ -147,7 +147,7 @@ pub fn get_relative_to(abs1: &Path, abs2: &Path) -> Path { assert!(len1 > 0); assert!(len2 > 0); - let max_common_path = uint::min(len1, len2) - 1; + let max_common_path = len1.min(&len2) - 1; let mut start_idx = 0; while start_idx < max_common_path && split1[start_idx] == split2[start_idx] { diff --git a/src/librustc/metadata/loader.rs b/src/librustc/metadata/loader.rs index 1ebf8f2e9f471..2cce75a2bae20 100644 --- a/src/librustc/metadata/loader.rs +++ b/src/librustc/metadata/loader.rs @@ -30,7 +30,6 @@ use core::option; use core::os::consts::{macos, freebsd, linux, android, win32}; use core::ptr; use core::str; -use core::uint; use core::vec; use extra::flate; @@ -215,7 +214,7 @@ fn get_metadata_section(os: os, let vlen = vec::len(encoder::metadata_encoding_version); debug!("checking %u bytes of metadata-version stamp", vlen); - let minsz = uint::min(vlen, csz); + let minsz = vlen.min(&csz); let mut version_ok = false; do vec::raw::buf_as_slice(cvbuf, minsz) |buf0| { version_ok = (buf0 == diff --git a/src/librustc/middle/check_match.rs b/src/librustc/middle/check_match.rs index 98f8efb72c80f..a9da504c86f24 100644 --- a/src/librustc/middle/check_match.rs +++ b/src/librustc/middle/check_match.rs @@ -246,7 +246,7 @@ pub fn is_useful(cx: @MatchCheckCtxt, m: &matrix, v: &[@pat]) -> useful { let max_len = do m.rev_iter().fold(0) |max_len, r| { match r[0].node { pat_vec(ref before, _, ref after) => { - uint::max(before.len() + after.len(), max_len) + (before.len() + after.len()).max(&max_len) } _ => max_len } diff --git a/src/librustc/middle/trans/cabi_arm.rs b/src/librustc/middle/trans/cabi_arm.rs index d59635ccd762f..2f9eee20dd545 100644 --- a/src/librustc/middle/trans/cabi_arm.rs +++ b/src/librustc/middle/trans/cabi_arm.rs @@ -19,7 +19,6 @@ use middle::trans::common::{T_array, T_ptr, T_void}; use core::iterator::IteratorUtil; use core::option::{Option, None, Some}; -use core::uint; fn align_up_to(off: uint, a: uint) -> uint { return (off + a - 1u) / a * a; @@ -44,7 +43,7 @@ fn ty_align(ty: TypeRef) -> uint { 1 } else { let str_tys = struct_tys(ty); - str_tys.iter().fold(1, |a, t| uint::max(a, ty_align(*t))) + str_tys.iter().fold(1u, |a, t| a.max(&ty_align(*t))) } } Array => { diff --git a/src/librustc/middle/trans/cabi_mips.rs b/src/librustc/middle/trans/cabi_mips.rs index 5ef5c4c35b103..bff68e6839183 100644 --- a/src/librustc/middle/trans/cabi_mips.rs +++ b/src/librustc/middle/trans/cabi_mips.rs @@ -13,7 +13,6 @@ use core::prelude::*; use core::iterator::IteratorUtil; use core::libc::c_uint; use core::ptr; -use core::uint; use core::vec; use lib::llvm::{llvm, TypeRef, Integer, Pointer, Float, Double}; use lib::llvm::{Struct, Array, Attribute}; @@ -58,7 +57,7 @@ fn ty_align(ty: TypeRef) -> uint { 1 } else { let str_tys = struct_tys(ty); - str_tys.iter().fold(1, |a, t| uint::max(a, ty_align(*t))) + str_tys.iter().fold(1u, |a, t| a.max(&ty_align(*t))) } } Array => { @@ -114,7 +113,7 @@ fn classify_arg_ty(ty: TypeRef, let size = ty_size(ty) * 8; let mut align = ty_align(ty); - align = uint::min(uint::max(align, 4), 8); + align = align.max(&4).min(&8); *offset = align_up_to(*offset, align); *offset += align_up_to(size, align * 8) / 8; diff --git a/src/librustc/middle/trans/cabi_x86_64.rs b/src/librustc/middle/trans/cabi_x86_64.rs index eb2d7e619eb75..54b63b8039f36 100644 --- a/src/librustc/middle/trans/cabi_x86_64.rs +++ b/src/librustc/middle/trans/cabi_x86_64.rs @@ -82,7 +82,7 @@ fn classify_ty(ty: TypeRef) -> ~[x86_64_reg_class] { 1 } else { let str_tys = struct_tys(ty); - str_tys.iter().fold(1, |a, t| uint::max(a, ty_align(*t))) + str_tys.iter().fold(1u, |a, t| a.max(&ty_align(*t))) } } Array => { diff --git a/src/librustc/rustc.rc b/src/librustc/rustc.rc index 0d26e4c6ef1e6..e1b9c4b34d022 100644 --- a/src/librustc/rustc.rc +++ b/src/librustc/rustc.rc @@ -53,7 +53,6 @@ use core::os; use core::result; use core::str; use core::task; -use core::uint; use core::vec; use extra::getopts::{groups, opt_present}; use extra::getopts; @@ -199,7 +198,7 @@ Available lint options: let lint_dict = lint::get_lint_dict(); let mut max_key = 0; - for lint_dict.each_key |k| { max_key = uint::max(k.len(), max_key); } + for lint_dict.each_key |k| { max_key = k.len().max(&max_key); } fn padded(max: uint, s: &str) -> ~str { str::from_bytes(vec::from_elem(max - s.len(), ' ' as u8)) + s } diff --git a/src/librustdoc/unindent_pass.rs b/src/librustdoc/unindent_pass.rs index b6753f385dfc1..5c545ce4ea347 100644 --- a/src/librustdoc/unindent_pass.rs +++ b/src/librustdoc/unindent_pass.rs @@ -73,7 +73,7 @@ fn unindent(s: &str) -> ~str { false } }; - uint::min(min_indent, spaces) + min_indent.min(&spaces) } }; diff --git a/src/libstd/cmp.rs b/src/libstd/cmp.rs index 55530f181a11b..13a1283394096 100644 --- a/src/libstd/cmp.rs +++ b/src/libstd/cmp.rs @@ -70,9 +70,9 @@ totaleq_impl!(char) /// Trait for testing approximate equality pub trait ApproxEq { - fn approx_epsilon() -> Eps; - fn approx_eq(&self, other: &Self) -> bool; - fn approx_eq_eps(&self, other: &Self, approx_epsilon: &Eps) -> bool; + pub fn approx_epsilon() -> Eps; + pub fn approx_eq(&self, other: &Self) -> bool; + pub fn approx_eq_eps(&self, other: &Self, approx_epsilon: &Eps) -> bool; } #[deriving(Clone, Eq)] diff --git a/src/libstd/hashmap.rs b/src/libstd/hashmap.rs index b1400d1bc76f4..767eb0358baac 100644 --- a/src/libstd/hashmap.rs +++ b/src/libstd/hashmap.rs @@ -18,6 +18,7 @@ use container::{Container, Mutable, Map, Set}; use cmp::{Eq, Equiv}; use hash::Hash; +use num::Orderable; use old_iter::BaseIter; use old_iter; use option::{None, Option, Some}; @@ -74,7 +75,7 @@ pub fn linear_map_with_capacity( fn linear_map_with_capacity_and_keys( k0: u64, k1: u64, initial_capacity: uint) -> HashMap { - let cap = uint::max(INITIAL_CAPACITY, initial_capacity); + let cap = INITIAL_CAPACITY.max(&initial_capacity); HashMap { k0: k0, k1: k1, resize_at: resize_at(cap), diff --git a/src/libstd/io.rs b/src/libstd/io.rs index e3977ca00674b..9058fcfb12262 100644 --- a/src/libstd/io.rs +++ b/src/libstd/io.rs @@ -55,9 +55,10 @@ use libc::{c_int, c_long, c_void, size_t, ssize_t}; use libc::consts::os::posix88::*; use os; use cast; -use path::Path; +use num::Orderable; use ops::Drop; use old_iter::{BaseIter, CopyableIter}; +use path::Path; use ptr; use result; use str; @@ -748,7 +749,7 @@ impl ReaderUtil for T { if self.eof() && line.is_empty() { break; } // trim the \n, so that each_line is consistent with read_line - let n = str::len(line); + let n = line.len(); if line[n-1] == '\n' as u8 { unsafe { str::raw::set_len(&mut line, n-1); } } @@ -1049,7 +1050,7 @@ pub struct BytesReader<'self> { impl<'self> Reader for BytesReader<'self> { fn read(&self, bytes: &mut [u8], len: uint) -> uint { - let count = uint::min(len, self.bytes.len() - *self.pos); + let count = len.min(&(self.bytes.len() - *self.pos)); let view = vec::slice(self.bytes, *self.pos, self.bytes.len()); vec::bytes::copy_memory(bytes, view, count); @@ -1650,7 +1651,7 @@ impl Writer for BytesWriter { let v_len = v.len(); let bytes = &mut *self.bytes; - let count = uint::max(bytes.len(), *self.pos + v_len); + let count = bytes.len().max(&(*self.pos + v_len)); vec::reserve(bytes, count); unsafe { diff --git a/src/libstd/num/f32.rs b/src/libstd/num/f32.rs index 62ce5ed65e10c..9cce5bf3385ed 100644 --- a/src/libstd/num/f32.rs +++ b/src/libstd/num/f32.rs @@ -20,10 +20,6 @@ use to_str; pub use cmath::c_float_targ_consts::*; -// An inner module is required to get the #[inline(always)] attribute on the -// functions. -pub use self::delegated::*; - macro_rules! delegate( ( $( @@ -34,6 +30,8 @@ macro_rules! delegate( ) -> $rv:ty = $bound_name:path ),* ) => ( + // An inner module is required to get the #[inline(always)] attribute on the + // functions. mod delegated { use cmath::c_float_utils; use libc::{c_float, c_int}; @@ -115,50 +113,6 @@ pub static infinity: f32 = 1.0_f32/0.0_f32; pub static neg_infinity: f32 = -1.0_f32/0.0_f32; -#[inline(always)] -pub fn add(x: f32, y: f32) -> f32 { return x + y; } - -#[inline(always)] -pub fn sub(x: f32, y: f32) -> f32 { return x - y; } - -#[inline(always)] -pub fn mul(x: f32, y: f32) -> f32 { return x * y; } - -#[inline(always)] -pub fn div(x: f32, y: f32) -> f32 { return x / y; } - -#[inline(always)] -pub fn rem(x: f32, y: f32) -> f32 { return x % y; } - -#[inline(always)] -pub fn lt(x: f32, y: f32) -> bool { return x < y; } - -#[inline(always)] -pub fn le(x: f32, y: f32) -> bool { return x <= y; } - -#[inline(always)] -pub fn eq(x: f32, y: f32) -> bool { return x == y; } - -#[inline(always)] -pub fn ne(x: f32, y: f32) -> bool { return x != y; } - -#[inline(always)] -pub fn ge(x: f32, y: f32) -> bool { return x >= y; } - -#[inline(always)] -pub fn gt(x: f32, y: f32) -> bool { return x > y; } - -#[inline(always)] -pub fn fmax(x: f32, y: f32) -> f32 { - if x >= y || y.is_NaN() { x } else { y } -} - -#[inline(always)] -pub fn fmin(x: f32, y: f32) -> f32 { - if x <= y || y.is_NaN() { x } else { y } -} - - // FIXME (#1999): replace the predicates below with llvm intrinsics or // calls to the libmath macros in the rust runtime for performance. @@ -221,15 +175,15 @@ impl Eq for f32 { #[cfg(not(test))] impl ApproxEq for f32 { #[inline(always)] - fn approx_epsilon() -> f32 { 1.0e-6 } + pub fn approx_epsilon() -> f32 { 1.0e-6 } #[inline(always)] - fn approx_eq(&self, other: &f32) -> bool { + pub fn approx_eq(&self, other: &f32) -> bool { self.approx_eq_eps(other, &ApproxEq::approx_epsilon::()) } #[inline(always)] - fn approx_eq_eps(&self, other: &f32, approx_epsilon: &f32) -> bool { + pub fn approx_eq_eps(&self, other: &f32, approx_epsilon: &f32) -> bool { (*self - *other).abs() < *approx_epsilon } } @@ -249,20 +203,30 @@ impl Ord for f32 { impl Orderable for f32 { /// Returns `NaN` if either of the numbers are `NaN`. #[inline(always)] - fn min(&self, other: &f32) -> f32 { - if self.is_NaN() || other.is_NaN() { Float::NaN() } else { fmin(*self, *other) } + pub fn min(&self, other: &f32) -> f32 { + cond!( + (self.is_NaN()) { *self } + (other.is_NaN()) { *other } + (*self < *other) { *self } + _ { *other } + ) } /// Returns `NaN` if either of the numbers are `NaN`. #[inline(always)] - fn max(&self, other: &f32) -> f32 { - if self.is_NaN() || other.is_NaN() { Float::NaN() } else { fmax(*self, *other) } + pub fn max(&self, other: &f32) -> f32 { + cond!( + (self.is_NaN()) { *self } + (other.is_NaN()) { *other } + (*self > *other) { *self } + _ { *other } + ) } /// Returns the number constrained within the range `mn <= self <= mx`. /// If any of the numbers are `NaN` then `NaN` is returned. #[inline(always)] - fn clamp(&self, mn: &f32, mx: &f32) -> f32 { + pub fn clamp(&self, mn: &f32, mx: &f32) -> f32 { cond!( (self.is_NaN()) { *self } (!(*self <= *mx)) { *mx } @@ -274,16 +238,16 @@ impl Orderable for f32 { impl Zero for f32 { #[inline(always)] - fn zero() -> f32 { 0.0 } + pub fn zero() -> f32 { 0.0 } /// Returns true if the number is equal to either `0.0` or `-0.0` #[inline(always)] - fn is_zero(&self) -> bool { *self == 0.0 || *self == -0.0 } + pub fn is_zero(&self) -> bool { *self == 0.0 || *self == -0.0 } } impl One for f32 { #[inline(always)] - fn one() -> f32 { 1.0 } + pub fn one() -> f32 { 1.0 } } #[cfg(not(test))] @@ -325,14 +289,14 @@ impl Neg for f32 { impl Signed for f32 { /// Computes the absolute value. Returns `NaN` if the number is `NaN`. #[inline(always)] - fn abs(&self) -> f32 { abs(*self) } + pub fn abs(&self) -> f32 { delegated::abs(*self) } /// /// The positive difference of two numbers. Returns `0.0` if the number is less than or /// equal to `other`, otherwise the difference between`self` and `other` is returned. /// #[inline(always)] - fn abs_sub(&self, other: &f32) -> f32 { abs_sub(*self, *other) } + pub fn abs_sub(&self, other: &f32) -> f32 { delegated::abs_sub(*self, *other) } /// /// # Returns @@ -342,35 +306,35 @@ impl Signed for f32 { /// - `NaN` if the number is NaN /// #[inline(always)] - fn signum(&self) -> f32 { - if self.is_NaN() { NaN } else { copysign(1.0, *self) } + pub fn signum(&self) -> f32 { + if self.is_NaN() { NaN } else { delegated::copysign(1.0, *self) } } /// Returns `true` if the number is positive, including `+0.0` and `infinity` #[inline(always)] - fn is_positive(&self) -> bool { *self > 0.0 || (1.0 / *self) == infinity } + pub fn is_positive(&self) -> bool { *self > 0.0 || (1.0 / *self) == infinity } /// Returns `true` if the number is negative, including `-0.0` and `neg_infinity` #[inline(always)] - fn is_negative(&self) -> bool { *self < 0.0 || (1.0 / *self) == neg_infinity } + pub fn is_negative(&self) -> bool { *self < 0.0 || (1.0 / *self) == neg_infinity } } impl Round for f32 { /// Round half-way cases toward `neg_infinity` #[inline(always)] - fn floor(&self) -> f32 { floor(*self) } + pub fn floor(&self) -> f32 { delegated::floor(*self) } /// Round half-way cases toward `infinity` #[inline(always)] - fn ceil(&self) -> f32 { ceil(*self) } + pub fn ceil(&self) -> f32 { delegated::ceil(*self) } /// Round half-way cases away from `0.0` #[inline(always)] - fn round(&self) -> f32 { round(*self) } + pub fn round(&self) -> f32 { delegated::round(*self) } /// The integer part of the number (rounds towards `0.0`) #[inline(always)] - fn trunc(&self) -> f32 { trunc(*self) } + pub fn trunc(&self) -> f32 { delegated::trunc(*self) } /// /// The fractional part of the number, satisfying: @@ -380,96 +344,94 @@ impl Round for f32 { /// ~~~ /// #[inline(always)] - fn fract(&self) -> f32 { *self - self.trunc() } + pub fn fract(&self) -> f32 { *self - self.trunc() } } impl Fractional for f32 { /// The reciprocal (multiplicative inverse) of the number #[inline(always)] - fn recip(&self) -> f32 { 1.0 / *self } + pub fn recip(&self) -> f32 { 1.0 / *self } } impl Algebraic for f32 { #[inline(always)] - fn pow(&self, n: f32) -> f32 { pow(*self, n) } + pub fn pow(&self, n: f32) -> f32 { delegated::pow(*self, n) } #[inline(always)] - fn sqrt(&self) -> f32 { sqrt(*self) } + pub fn sqrt(&self) -> f32 { delegated::sqrt(*self) } #[inline(always)] - fn rsqrt(&self) -> f32 { self.sqrt().recip() } + pub fn rsqrt(&self) -> f32 { self.sqrt().recip() } #[inline(always)] - fn cbrt(&self) -> f32 { cbrt(*self) } + pub fn cbrt(&self) -> f32 { delegated::cbrt(*self) } #[inline(always)] - fn hypot(&self, other: f32) -> f32 { hypot(*self, other) } + pub fn hypot(&self, other: f32) -> f32 { delegated::hypot(*self, other) } } impl Trigonometric for f32 { #[inline(always)] - fn sin(&self) -> f32 { sin(*self) } + pub fn sin(&self) -> f32 { delegated::sin(*self) } #[inline(always)] - fn cos(&self) -> f32 { cos(*self) } + pub fn cos(&self) -> f32 { delegated::cos(*self) } #[inline(always)] - fn tan(&self) -> f32 { tan(*self) } + pub fn tan(&self) -> f32 { delegated::tan(*self) } #[inline(always)] - fn asin(&self) -> f32 { asin(*self) } + pub fn asin(&self) -> f32 { delegated::asin(*self) } #[inline(always)] - fn acos(&self) -> f32 { acos(*self) } + pub fn acos(&self) -> f32 { delegated::acos(*self) } #[inline(always)] - fn atan(&self) -> f32 { atan(*self) } + pub fn atan(&self) -> f32 { delegated::atan(*self) } #[inline(always)] - fn atan2(&self, other: f32) -> f32 { atan2(*self, other) } + pub fn atan2(&self, other: f32) -> f32 { delegated::atan2(*self, other) } /// Simultaneously computes the sine and cosine of the number #[inline(always)] - fn sin_cos(&self) -> (f32, f32) { - (self.sin(), self.cos()) - } + pub fn sin_cos(&self) -> (f32, f32) { (self.sin(), self.cos()) } } impl Exponential for f32 { /// Returns the exponential of the number #[inline(always)] - fn exp(&self) -> f32 { exp(*self) } + pub fn exp(&self) -> f32 { delegated::exp(*self) } /// Returns 2 raised to the power of the number #[inline(always)] - fn exp2(&self) -> f32 { exp2(*self) } + pub fn exp2(&self) -> f32 { delegated::exp2(*self) } /// Returns the natural logarithm of the number #[inline(always)] - fn ln(&self) -> f32 { ln(*self) } + pub fn ln(&self) -> f32 { delegated::ln(*self) } /// Returns the logarithm of the number with respect to an arbitrary base #[inline(always)] - fn log(&self, base: f32) -> f32 { self.ln() / base.ln() } + pub fn log(&self, base: f32) -> f32 { self.ln() / base.ln() } /// Returns the base 2 logarithm of the number #[inline(always)] - fn log2(&self) -> f32 { log2(*self) } + pub fn log2(&self) -> f32 { delegated::log2(*self) } /// Returns the base 10 logarithm of the number #[inline(always)] - fn log10(&self) -> f32 { log10(*self) } + pub fn log10(&self) -> f32 { delegated::log10(*self) } } impl Hyperbolic for f32 { #[inline(always)] - fn sinh(&self) -> f32 { sinh(*self) } + pub fn sinh(&self) -> f32 { delegated::sinh(*self) } #[inline(always)] - fn cosh(&self) -> f32 { cosh(*self) } + pub fn cosh(&self) -> f32 { delegated::cosh(*self) } #[inline(always)] - fn tanh(&self) -> f32 { tanh(*self) } + pub fn tanh(&self) -> f32 { delegated::tanh(*self) } /// /// Inverse hyperbolic sine @@ -481,7 +443,7 @@ impl Hyperbolic for f32 { /// - `NaN` if `self` is `NaN` /// #[inline(always)] - fn asinh(&self) -> f32 { + pub fn asinh(&self) -> f32 { match *self { neg_infinity => neg_infinity, x => (x + ((x * x) + 1.0).sqrt()).ln(), @@ -498,7 +460,7 @@ impl Hyperbolic for f32 { /// - `NaN` if `self` is `NaN` or `self < 1.0` (including `neg_infinity`) /// #[inline(always)] - fn acosh(&self) -> f32 { + pub fn acosh(&self) -> f32 { match *self { x if x < 1.0 => Float::NaN(), x => (x + ((x * x) - 1.0).sqrt()).ln(), @@ -518,143 +480,198 @@ impl Hyperbolic for f32 { /// (including `infinity` and `neg_infinity`) /// #[inline(always)] - fn atanh(&self) -> f32 { + pub fn atanh(&self) -> f32 { 0.5 * ((2.0 * *self) / (1.0 - *self)).ln_1p() } } +impl Interpolate for f32 { + pub fn linear(x: f32, y: f32, t: f32) -> f32 { + t.mul_add(y - x, x) + } + + pub fn cosine(x: f32, y: f32, t: f32) -> f32 { + (0.5 * (1.0 - (t * Real::pi()).cos())).mul_add(y - x, x) + } + + pub fn smooth(x: f32, y: f32, t: f32) -> f32 { + (t * t * t.mul_add(-2.0, 3.0)).mul_add(y - x, x) + } + + pub fn barycentric(x: f32, y: f32, z: f32, t0: f32, t1: f32) -> f32 { + let t2 = 1.0 - t0 - t1; + + t0 * x + t1 * y + t2 * z + } + + pub fn hermite(x: f32, xp: f32, y: f32, yp: f32, t: f32) -> f32 { + let a0 = t.mul_add(t * t.mul_add(2.0, -3.0), 1.0); + let a1 = t * t * t.mul_add(-2.0, 3.0); + let a2 = t * t.mul_add(t * (t - 2.0), 1.0); + let a3 = t * t * (t - 1.0); + + a0 * x + a1 * y + a2 * xp + a3 * yp + } + + pub fn cubic(x: f32, y: f32, z: f32, u: f32, t: f32) -> f32 { + let a0 = -x + y - z + u; + let a1 = x - y - a0; + let a2 = z - x; + let a3 = y; + + t.mul_add(t.mul_add(t.mul_add((t * a0), a1), a2), a3) + } + + pub fn catmull_rom(x: f32, y: f32, z: f32, u: f32, t: f32) -> f32 { + let a0 = -x + 3.0 * y - 3.0 * z + u; + let a1 = 2.0 * x - 5.0 * y + 4.0 * z - u; + let a2 = -x + z; + let a3 = 2.0 * y; + + 0.5 * t.mul_add(t.mul_add(t.mul_add((t * a0), a1), a2), a3) + } +} + impl Real for f32 { /// Archimedes' constant #[inline(always)] - fn pi() -> f32 { 3.14159265358979323846264338327950288 } + pub fn pi() -> f32 { 3.14159265358979323846264338327950288 } /// 2.0 * pi #[inline(always)] - fn two_pi() -> f32 { 6.28318530717958647692528676655900576 } + pub fn two_pi() -> f32 { 6.28318530717958647692528676655900576 } /// pi / 2.0 #[inline(always)] - fn frac_pi_2() -> f32 { 1.57079632679489661923132169163975144 } + pub fn frac_pi_2() -> f32 { 1.57079632679489661923132169163975144 } /// pi / 3.0 #[inline(always)] - fn frac_pi_3() -> f32 { 1.04719755119659774615421446109316763 } + pub fn frac_pi_3() -> f32 { 1.04719755119659774615421446109316763 } /// pi / 4.0 #[inline(always)] - fn frac_pi_4() -> f32 { 0.785398163397448309615660845819875721 } + pub fn frac_pi_4() -> f32 { 0.785398163397448309615660845819875721 } /// pi / 6.0 #[inline(always)] - fn frac_pi_6() -> f32 { 0.52359877559829887307710723054658381 } + pub fn frac_pi_6() -> f32 { 0.52359877559829887307710723054658381 } /// pi / 8.0 #[inline(always)] - fn frac_pi_8() -> f32 { 0.39269908169872415480783042290993786 } + pub fn frac_pi_8() -> f32 { 0.39269908169872415480783042290993786 } /// 1 .0/ pi #[inline(always)] - fn frac_1_pi() -> f32 { 0.318309886183790671537767526745028724 } + pub fn frac_1_pi() -> f32 { 0.318309886183790671537767526745028724 } /// 2.0 / pi #[inline(always)] - fn frac_2_pi() -> f32 { 0.636619772367581343075535053490057448 } + pub fn frac_2_pi() -> f32 { 0.636619772367581343075535053490057448 } /// 2.0 / sqrt(pi) #[inline(always)] - fn frac_2_sqrtpi() -> f32 { 1.12837916709551257389615890312154517 } + pub fn frac_2_sqrtpi() -> f32 { 1.12837916709551257389615890312154517 } /// sqrt(2.0) #[inline(always)] - fn sqrt2() -> f32 { 1.41421356237309504880168872420969808 } + pub fn sqrt2() -> f32 { 1.41421356237309504880168872420969808 } /// 1.0 / sqrt(2.0) #[inline(always)] - fn frac_1_sqrt2() -> f32 { 0.707106781186547524400844362104849039 } + pub fn frac_1_sqrt2() -> f32 { 0.707106781186547524400844362104849039 } /// Euler's number #[inline(always)] - fn e() -> f32 { 2.71828182845904523536028747135266250 } + pub fn e() -> f32 { 2.71828182845904523536028747135266250 } /// log2(e) #[inline(always)] - fn log2_e() -> f32 { 1.44269504088896340735992468100189214 } + pub fn log2_e() -> f32 { 1.44269504088896340735992468100189214 } /// log10(e) #[inline(always)] - fn log10_e() -> f32 { 0.434294481903251827651128918916605082 } + pub fn log10_e() -> f32 { 0.434294481903251827651128918916605082 } /// ln(2.0) #[inline(always)] - fn ln_2() -> f32 { 0.693147180559945309417232121458176568 } + pub fn ln_2() -> f32 { 0.693147180559945309417232121458176568 } /// ln(10.0) #[inline(always)] - fn ln_10() -> f32 { 2.30258509299404568401799145468436421 } + pub fn ln_10() -> f32 { 2.30258509299404568401799145468436421 } + + /// Returns the error function of the number + #[inline(always)] + pub fn erf(&self) -> f32 { delegated::erf(*self) } + + /// Returns the complementary error function of the number + #[inline(always)] + pub fn erfc(&self) -> f32 { delegated::erfc(*self) } /// Converts to degrees, assuming the number is in radians #[inline(always)] - fn to_degrees(&self) -> f32 { *self * (180.0 / Real::pi::()) } + pub fn to_degrees(&self) -> f32 { *self * (180.0 / Real::pi::()) } /// Converts to radians, assuming the number is in degrees #[inline(always)] - fn to_radians(&self) -> f32 { *self * (Real::pi::() / 180.0) } + pub fn to_radians(&self) -> f32 { *self * (Real::pi::() / 180.0) } } impl Bounded for f32 { #[inline(always)] - fn min_value() -> f32 { 1.17549435e-38 } + pub fn min_value() -> f32 { 1.17549435e-38 } #[inline(always)] - fn max_value() -> f32 { 3.40282347e+38 } + pub fn max_value() -> f32 { 3.40282347e+38 } } impl Primitive for f32 { #[inline(always)] - fn bits() -> uint { 32 } + pub fn bits() -> uint { 32 } #[inline(always)] - fn bytes() -> uint { Primitive::bits::() / 8 } + pub fn bytes() -> uint { Primitive::bits::() / 8 } } impl Float for f32 { #[inline(always)] - fn NaN() -> f32 { 0.0 / 0.0 } + pub fn NaN() -> f32 { 0.0 / 0.0 } #[inline(always)] - fn infinity() -> f32 { 1.0 / 0.0 } + pub fn infinity() -> f32 { 1.0 / 0.0 } #[inline(always)] - fn neg_infinity() -> f32 { -1.0 / 0.0 } + pub fn neg_infinity() -> f32 { -1.0 / 0.0 } #[inline(always)] - fn neg_zero() -> f32 { -0.0 } + pub fn neg_zero() -> f32 { -0.0 } /// Returns `true` if the number is NaN #[inline(always)] - fn is_NaN(&self) -> bool { *self != *self } + pub fn is_NaN(&self) -> bool { *self != *self } /// Returns `true` if the number is infinite #[inline(always)] - fn is_infinite(&self) -> bool { + pub fn is_infinite(&self) -> bool { *self == Float::infinity() || *self == Float::neg_infinity() } /// Returns `true` if the number is neither infinite or NaN #[inline(always)] - fn is_finite(&self) -> bool { + pub fn is_finite(&self) -> bool { !(self.is_NaN() || self.is_infinite()) } /// Returns `true` if the number is neither zero, infinite, subnormal or NaN #[inline(always)] - fn is_normal(&self) -> bool { + pub fn is_normal(&self) -> bool { self.classify() == FPNormal } /// Returns the floating point category of the number. If only one property is going to /// be tested, it is generally faster to use the specific predicate instead. - fn classify(&self) -> FPCategory { + pub fn classify(&self) -> FPCategory { static EXP_MASK: u32 = 0x7f800000; static MAN_MASK: u32 = 0x007fffff; @@ -671,30 +688,30 @@ impl Float for f32 { } #[inline(always)] - fn mantissa_digits() -> uint { 24 } + pub fn mantissa_digits() -> uint { 24 } #[inline(always)] - fn digits() -> uint { 6 } + pub fn digits() -> uint { 6 } #[inline(always)] - fn epsilon() -> f32 { 1.19209290e-07 } + pub fn epsilon() -> f32 { 1.19209290e-07 } #[inline(always)] - fn min_exp() -> int { -125 } + pub fn min_exp() -> int { -125 } #[inline(always)] - fn max_exp() -> int { 128 } + pub fn max_exp() -> int { 128 } #[inline(always)] - fn min_10_exp() -> int { -37 } + pub fn min_10_exp() -> int { -37 } #[inline(always)] - fn max_10_exp() -> int { 38 } + pub fn max_10_exp() -> int { 38 } /// Constructs a floating point number by multiplying `x` by 2 raised to the power of `exp` #[inline(always)] - fn ldexp(x: f32, exp: int) -> f32 { - ldexp(x, exp as c_int) + pub fn ldexp(x: f32, exp: int) -> f32 { + delegated::ldexp(x, exp as c_int) } /// @@ -704,9 +721,9 @@ impl Float for f32 { /// - `0.5 <= abs(x) < 1.0` /// #[inline(always)] - fn frexp(&self) -> (f32, int) { + pub fn frexp(&self) -> (f32, int) { let mut exp = 0; - let x = frexp(*self, &mut exp); + let x = delegated::frexp(*self, &mut exp); (x, exp as int) } @@ -715,14 +732,14 @@ impl Float for f32 { /// even if the number is close to zero /// #[inline(always)] - fn exp_m1(&self) -> f32 { exp_m1(*self) } + pub fn exp_m1(&self) -> f32 { delegated::exp_m1(*self) } /// /// Returns the natural logarithm of the number plus `1` (`ln(1+n)`) more accurately /// than if the operations were performed separately /// #[inline(always)] - fn ln_1p(&self) -> f32 { ln_1p(*self) } + pub fn ln_1p(&self) -> f32 { delegated::ln_1p(*self) } /// /// Fused multiply-add. Computes `(self * a) + b` with only one rounding error. This @@ -730,14 +747,14 @@ impl Float for f32 { /// operation followed by an add. /// #[inline(always)] - fn mul_add(&self, a: f32, b: f32) -> f32 { - mul_add(*self, a, b) + pub fn mul_add(&self, a: f32, b: f32) -> f32 { + delegated::mul_add(*self, a, b) } /// Returns the next representable floating-point value in the direction of `other` #[inline(always)] - fn next_after(&self, other: f32) -> f32 { - next_after(*self, other) + pub fn next_after(&self, other: f32) -> f32 { + delegated::next_after(*self, other) } } @@ -850,7 +867,7 @@ impl to_str::ToStr for f32 { impl num::ToStrRadix for f32 { #[inline(always)] - fn to_str_radix(&self, rdx: uint) -> ~str { + pub fn to_str_radix(&self, rdx: uint) -> ~str { to_str_radix(*self, rdx) } } @@ -953,7 +970,7 @@ impl FromStr for f32 { impl num::FromStrRadix for f32 { #[inline(always)] - fn from_str_radix(val: &str, rdx: uint) -> Option { + pub fn from_str_radix(val: &str, rdx: uint) -> Option { from_str_radix(val, rdx) } } @@ -976,12 +993,16 @@ mod tests { fn test_min() { assert_eq!(1f32.min(&2f32), 1f32); assert_eq!(2f32.min(&1f32), 1f32); + assert!(1f32.min(&Float::NaN::()).is_NaN()); + assert!(Float::NaN::().min(&1f32).is_NaN()); } #[test] fn test_max() { assert_eq!(1f32.max(&2f32), 2f32); assert_eq!(2f32.max(&1f32), 2f32); + assert!(1f32.max(&Float::NaN::()).is_NaN()); + assert!(Float::NaN::().max(&1f32).is_NaN()); } #[test] @@ -1101,6 +1122,192 @@ mod tests { assert_approx_eq!((-0.5f32).atanh(), -0.54930614433405484569762261846126285f32); } + #[test] + fn test_linear() { + assert_eq!(Interpolate::linear(3.0f32, 5.0f32, 0.0f32), 3.0f32); + assert_eq!(Interpolate::linear(3.0f32, 5.0f32, 0.5f32), 4.0f32); + assert_eq!(Interpolate::linear(3.0f32, 5.0f32, 1.0f32), 5.0f32); + + assert_eq!(Interpolate::linear(3.0f32, 5.0f32, infinity), infinity); + assert_eq!(Interpolate::linear(3.0f32, 5.0f32, -infinity), -infinity); + + assert_eq!(Interpolate::linear(3.0f32, infinity, 0.5f32), infinity); + assert_eq!(Interpolate::linear(3.0f32, -infinity, 0.5f32), -infinity); + + assert!(Interpolate::linear( infinity, 5.0f32, 0.5f32).is_NaN()); + assert!(Interpolate::linear(-infinity, 5.0f32, 0.5f32).is_NaN()); + + assert!(Interpolate::linear( infinity, 5.0f32, 1.0f32).is_NaN()); + assert!(Interpolate::linear(-infinity, 5.0f32, 1.0f32).is_NaN()); + + assert!(Interpolate::linear(NaN, 5.0f32, 1.0f32).is_NaN()); + assert!(Interpolate::linear(3.0f32, NaN, 1.0f32).is_NaN()); + assert!(Interpolate::linear(3.0f32, 5.0f32, NaN).is_NaN()); + } + + #[test] + fn test_cosine() { + assert_eq!(Interpolate::cosine(3.0f32, 5.0f32, 0.0f32), 3.0f32); + assert_eq!(Interpolate::cosine(3.0f32, 5.0f32, 0.5f32), 4.0f32); + assert_eq!(Interpolate::cosine(3.0f32, 5.0f32, 1.0f32), 5.0f32); + + assert!(Interpolate::cosine(3.0f32, 5.0f32, infinity).is_NaN()); + assert!(Interpolate::cosine(3.0f32, 5.0f32, -infinity).is_NaN()); + + assert_eq!(Interpolate::cosine(3.0f32, infinity, 0.5f32), infinity); + assert_eq!(Interpolate::cosine(3.0f32, -infinity, 0.5f32), -infinity); + + assert!(Interpolate::cosine( infinity, 5.0f32, 0.5f32).is_NaN()); + assert!(Interpolate::cosine(-infinity, 5.0f32, 0.5f32).is_NaN()); + + assert!(Interpolate::cosine( infinity, 5.0f32, 1.0f32).is_NaN()); + assert!(Interpolate::cosine(-infinity, 5.0f32, 1.0f32).is_NaN()); + + assert!(Interpolate::cosine(NaN, 5.0f32, 1.0f32).is_NaN()); + assert!(Interpolate::cosine(3.0f32, NaN, 1.0f32).is_NaN()); + assert!(Interpolate::cosine(3.0f32, 5.0f32, NaN).is_NaN()); + } + + #[test] + fn test_smooth() { + assert_eq!(Interpolate::smooth(3.0f32, 5.0f32, 0.0f32), 3.0f32); + assert_eq!(Interpolate::smooth(3.0f32, 5.0f32, 0.5f32), 4.0f32); + assert_eq!(Interpolate::smooth(3.0f32, 5.0f32, 1.0f32), 5.0f32); + + assert_eq!(Interpolate::smooth(3.0f32, 5.0f32, infinity), -infinity); + assert_eq!(Interpolate::smooth(3.0f32, 5.0f32, -infinity), infinity); + + assert_eq!(Interpolate::smooth(3.0f32, infinity, 0.5f32), infinity); + assert_eq!(Interpolate::smooth(3.0f32, -infinity, 0.5f32), -infinity); + + assert!(Interpolate::smooth( infinity, 5.0f32, 0.5f32).is_NaN()); + assert!(Interpolate::smooth(-infinity, 5.0f32, 0.5f32).is_NaN()); + + assert!(Interpolate::smooth( infinity, 5.0f32, 1.0f32).is_NaN()); + assert!(Interpolate::smooth(-infinity, 5.0f32, 1.0f32).is_NaN()); + + assert!(Interpolate::smooth(NaN, 5.0f32, 1.0f32).is_NaN()); + assert!(Interpolate::smooth(3.0f32, NaN, 1.0f32).is_NaN()); + assert!(Interpolate::smooth(3.0f32, 5.0f32, NaN).is_NaN()); + } + + #[test] + fn test_barycentric() { + assert_eq!(Interpolate::barycentric(3.00f32, 0.50f32, 1.00f32, 0.00f32, 0.00f32), 1.00f32); + assert_eq!(Interpolate::barycentric(3.00f32, 0.50f32, 1.00f32, 1.00f32, 0.00f32), 3.00f32); + assert_eq!(Interpolate::barycentric(3.00f32, 0.50f32, 1.00f32, 0.00f32, 1.00f32), 0.50f32); + assert_eq!(Interpolate::barycentric(3.00f32, 0.50f32, 1.00f32, 0.50f32, 0.50f32), 1.75f32); + assert_eq!(Interpolate::barycentric(3.00f32, 0.50f32, 1.00f32, 0.00f32, 0.50f32), 0.75f32); + assert_eq!(Interpolate::barycentric(3.00f32, 0.50f32, 1.00f32, 0.50f32, 0.00f32), 2.00f32); + assert_eq!(Interpolate::barycentric(1.25f32, 2.50f32, 5.00f32, 0.40f32, 0.40f32), 2.50f32); + + assert_eq!(Interpolate::barycentric(infinity, 4.0f32, 6.0f32, 0.2f32, 0.1f32), infinity); + assert_eq!(Interpolate::barycentric(1.0f32, infinity, 6.0f32, 0.2f32, 0.1f32), infinity); + assert_eq!(Interpolate::barycentric(1.0f32, 4.0f32, infinity, 0.2f32, 0.1f32), infinity); + assert!(Interpolate::barycentric(1.0f32, 4.0f32, 6.0f32, infinity, 0.1f32).is_NaN()); + assert!(Interpolate::barycentric(1.0f32, 4.0f32, 6.0f32, 0.2f32, infinity).is_NaN()); + + assert_eq!(Interpolate::barycentric(-infinity, 4.0f32, 6.0f32, 0.2f32, 0.1f32), -infinity); + assert_eq!(Interpolate::barycentric(1.0f32, -infinity, 6.0f32, 0.2f32, 0.1f32), -infinity); + assert_eq!(Interpolate::barycentric(1.0f32, 4.0f32, -infinity, 0.2f32, 0.1f32), -infinity); + assert!(Interpolate::barycentric(1.0f32, 4.0f32, 6.0f32, -infinity, 0.1f32).is_NaN()); + assert!(Interpolate::barycentric(1.0f32, 4.0f32, 6.0f32, 0.2f32, -infinity).is_NaN()); + + assert!(Interpolate::barycentric(NaN, 4.0f32, 6.0f32, 0.0f32, 0.0f32).is_NaN()); + assert!(Interpolate::barycentric(1.0f32, NaN, 6.0f32, 0.2f32, 0.0f32).is_NaN()); + assert!(Interpolate::barycentric(1.0f32, 4.0f32, NaN, 0.4f32, 0.0f32).is_NaN()); + assert!(Interpolate::barycentric(1.0f32, 4.0f32, 6.0f32, NaN, 0.0f32).is_NaN()); + assert!(Interpolate::barycentric(1.0f32, 4.0f32, 6.0f32, 0.4f32, NaN).is_NaN()); + } + + #[test] + fn test_hermite() { + assert_eq!(Interpolate::hermite(3.0f32, 0.0f32, 5.0f32, 0.0f32, 0.0f32), 3.0f32); + assert_eq!(Interpolate::hermite(3.0f32, 0.0f32, 5.0f32, 0.0f32, 0.5f32), 4.0f32); + assert_eq!(Interpolate::hermite(3.0f32, 0.0f32, 5.0f32, 0.0f32, 1.0f32), 5.0f32); + + assert_eq!(Interpolate::hermite(3.0f32, 1.0f32, -5.0f32, 2.0f32, infinity), infinity); + assert_eq!(Interpolate::hermite(3.0f32, -1.0f32, -5.0f32, 2.0f32, -infinity), -infinity); + + assert!(Interpolate::hermite(3.0f32, 0.0f32, 5.0f32, 0.0f32, infinity).is_NaN()); + assert!(Interpolate::hermite(3.0f32, 0.0f32, 5.0f32, 0.0f32, -infinity).is_NaN()); + + assert!(Interpolate::hermite(3.0f32, -1.0f32, 5.0f32, 2.0f32, infinity).is_NaN()); + assert!(Interpolate::hermite(3.0f32, -1.0f32, 5.0f32, 2.0f32, -infinity).is_NaN()); + + assert_eq!(Interpolate::hermite(3.0f32, 0.0f32, infinity, 0.0f32, 0.5f32), infinity); + assert_eq!(Interpolate::hermite(3.0f32, 0.0f32, -infinity, 0.0f32, 0.5f32), -infinity); + + assert!(Interpolate::hermite(3.0f32, 0.0f32, infinity, 0.0f32, 0.0f32).is_NaN()); + assert!(Interpolate::hermite(3.0f32, 0.0f32, -infinity, 0.0f32, 0.0f32).is_NaN()); + + assert_eq!(Interpolate::hermite( infinity, 0.0f32, 5.0f32, 0.0f32, 0.5f32), infinity); + assert_eq!(Interpolate::hermite(-infinity, 0.0f32, 5.0f32, 0.0f32, 0.5f32), -infinity); + + assert!(Interpolate::hermite( infinity, 0.0f32, 5.0f32, 0.0f32, 1.0f32).is_NaN()); + assert!(Interpolate::hermite(-infinity, 0.0f32, 5.0f32, 0.0f32, 1.0f32).is_NaN()); + + assert!(Interpolate::hermite(NaN, 0.0f32, 5.0f32, 0.0f32, 1.0f32).is_NaN()); + assert!(Interpolate::hermite(3.0f32, NaN, 5.0f32, 0.0f32, 1.0f32).is_NaN()); + assert!(Interpolate::hermite(3.0f32, 0.0f32, NaN, 0.0f32, 1.0f32).is_NaN()); + assert!(Interpolate::hermite(3.0f32, 0.0f32, 5.0f32, NaN, 1.0f32).is_NaN()); + assert!(Interpolate::hermite(3.0f32, 0.0f32, 5.0f32, 0.0f32, NaN).is_NaN()); + } + + #[test] + fn test_cubic() { + assert_eq!(Interpolate::cubic(1.0f32, 3.0f32, 5.0f32, 6.0f32, 0.0f32), 3.0f32); + assert_eq!(Interpolate::cubic(1.0f32, 3.0f32, 5.0f32, 6.0f32, 1.0f32), 5.0f32); + + assert_eq!(Interpolate::cubic(1.0f32, 3.0f32, 5.0f32, 6.0f32, infinity), infinity); + assert_eq!(Interpolate::cubic(1.0f32, 3.0f32, 5.0f32, 6.0f32, -infinity), infinity); + + assert!(Interpolate::cubic( infinity, 3.0f32, 5.0f32, 6.0f32, 0.5f32).is_NaN()); + assert!(Interpolate::cubic(-infinity, 3.0f32, 5.0f32, 6.0f32, 0.5f32).is_NaN()); + + assert!(Interpolate::cubic(1.0f32, infinity, 5.0f32, 6.0f32, 0.5f32).is_NaN()); + assert!(Interpolate::cubic(1.0f32, -infinity, 5.0f32, 6.0f32, 0.5f32).is_NaN()); + + assert!(Interpolate::cubic(1.0f32, 3.0f32, infinity, 6.0f32, 0.5f32).is_NaN()); + assert!(Interpolate::cubic(1.0f32, 3.0f32, -infinity, 6.0f32, 0.5f32).is_NaN()); + + assert!(Interpolate::cubic(1.0f32, 3.0f32, 5.0f32, infinity, 0.5f32).is_NaN()); + assert!(Interpolate::cubic(1.0f32, 3.0f32, 5.0f32, -infinity, 0.5f32).is_NaN()); + + assert!(Interpolate::cubic( NaN, 3.0f32, 5.0f32, 6.0f32, 0.5f32).is_NaN()); + assert!(Interpolate::cubic(1.0f32, NaN, 5.0f32, 6.0f32, 0.5f32).is_NaN()); + assert!(Interpolate::cubic(1.0f32, 3.0f32, NaN, 6.0f32, 0.5f32).is_NaN()); + assert!(Interpolate::cubic(1.0f32, 3.0f32, 5.0f32, NaN, 0.5f32).is_NaN()); + assert!(Interpolate::cubic(1.0f32, 3.0f32, 5.0f32, 6.0f32, NaN).is_NaN()); + } + + #[test] + fn test_catmull_rom() { + assert_eq!(Interpolate::catmull_rom(1.0f32, 3.0f32, 5.0f32, 6.0f32, 0.0f32), 3.0f32); + assert_eq!(Interpolate::catmull_rom(1.0f32, 3.0f32, 5.0f32, 6.0f32, 1.0f32), 5.0f32); + + assert_eq!(Interpolate::catmull_rom(1.0f32, 3.0f32, 5.0f32, 6.0f32, infinity), -infinity); + assert_eq!(Interpolate::catmull_rom(1.0f32, 3.0f32, 5.0f32, 6.0f32, -infinity), -infinity); + + assert!(Interpolate::catmull_rom( infinity, 3.0f32, 5.0f32, 6.0f32, 0.5f32).is_NaN()); + assert!(Interpolate::catmull_rom(-infinity, 3.0f32, 5.0f32, 6.0f32, 0.5f32).is_NaN()); + + assert!(Interpolate::catmull_rom(1.0f32, infinity, 5.0f32, 6.0f32, 0.5f32).is_NaN()); + assert!(Interpolate::catmull_rom(1.0f32, -infinity, 5.0f32, 6.0f32, 0.5f32).is_NaN()); + + assert!(Interpolate::catmull_rom(1.0f32, 3.0f32, infinity, 6.0f32, 0.5f32).is_NaN()); + assert!(Interpolate::catmull_rom(1.0f32, 3.0f32, -infinity, 6.0f32, 0.5f32).is_NaN()); + + assert!(Interpolate::catmull_rom(1.0f32, 3.0f32, 5.0f32, infinity, 0.5f32).is_NaN()); + assert!(Interpolate::catmull_rom(1.0f32, 3.0f32, 5.0f32, -infinity, 0.5f32).is_NaN()); + + assert!(Interpolate::catmull_rom(NaN, 3.0f32, 5.0f32, 6.0f32, 0.5f32).is_NaN()); + assert!(Interpolate::catmull_rom(1.0f32, NaN, 5.0f32, 6.0f32, 0.5f32).is_NaN()); + assert!(Interpolate::catmull_rom(1.0f32, 3.0f32, NaN, 6.0f32, 0.5f32).is_NaN()); + assert!(Interpolate::catmull_rom(1.0f32, 3.0f32, 5.0f32, NaN, 0.5f32).is_NaN()); + assert!(Interpolate::catmull_rom(1.0f32, 3.0f32, 5.0f32, 6.0f32, NaN).is_NaN()); + } + #[test] fn test_real_consts() { assert_approx_eq!(Real::two_pi::(), 2f32 * Real::pi::()); diff --git a/src/libstd/num/f64.rs b/src/libstd/num/f64.rs index de44d861645b3..3ded06d877708 100644 --- a/src/libstd/num/f64.rs +++ b/src/libstd/num/f64.rs @@ -20,11 +20,6 @@ use prelude::*; use to_str; pub use cmath::c_double_targ_consts::*; -pub use cmp::{min, max}; - -// An inner module is required to get the #[inline(always)] attribute on the -// functions. -pub use self::delegated::*; macro_rules! delegate( ( @@ -36,6 +31,8 @@ macro_rules! delegate( ) -> $rv:ty = $bound_name:path ),* ) => ( + // An inner module is required to get the #[inline(always)] attribute on the + // functions. mod delegated { use cmath::c_double_utils; use libc::{c_double, c_int}; @@ -141,49 +138,6 @@ pub static infinity: f64 = 1.0_f64/0.0_f64; pub static neg_infinity: f64 = -1.0_f64/0.0_f64; -#[inline(always)] -pub fn add(x: f64, y: f64) -> f64 { return x + y; } - -#[inline(always)] -pub fn sub(x: f64, y: f64) -> f64 { return x - y; } - -#[inline(always)] -pub fn mul(x: f64, y: f64) -> f64 { return x * y; } - -#[inline(always)] -pub fn div(x: f64, y: f64) -> f64 { return x / y; } - -#[inline(always)] -pub fn rem(x: f64, y: f64) -> f64 { return x % y; } - -#[inline(always)] -pub fn lt(x: f64, y: f64) -> bool { return x < y; } - -#[inline(always)] -pub fn le(x: f64, y: f64) -> bool { return x <= y; } - -#[inline(always)] -pub fn eq(x: f64, y: f64) -> bool { return x == y; } - -#[inline(always)] -pub fn ne(x: f64, y: f64) -> bool { return x != y; } - -#[inline(always)] -pub fn ge(x: f64, y: f64) -> bool { return x >= y; } - -#[inline(always)] -pub fn gt(x: f64, y: f64) -> bool { return x > y; } - -#[inline(always)] -pub fn fmax(x: f64, y: f64) -> f64 { - if x >= y || y.is_NaN() { x } else { y } -} - -#[inline(always)] -pub fn fmin(x: f64, y: f64) -> f64 { - if x <= y || y.is_NaN() { x } else { y } -} - // FIXME (#1999): add is_normal, is_subnormal, and fpclassify /* Module: consts */ @@ -243,15 +197,15 @@ impl Eq for f64 { #[cfg(not(test))] impl ApproxEq for f64 { #[inline(always)] - fn approx_epsilon() -> f64 { 1.0e-6 } + pub fn approx_epsilon() -> f64 { 1.0e-6 } #[inline(always)] - fn approx_eq(&self, other: &f64) -> bool { + pub fn approx_eq(&self, other: &f64) -> bool { self.approx_eq_eps(other, &ApproxEq::approx_epsilon::()) } #[inline(always)] - fn approx_eq_eps(&self, other: &f64, approx_epsilon: &f64) -> bool { + pub fn approx_eq_eps(&self, other: &f64, approx_epsilon: &f64) -> bool { (*self - *other).abs() < *approx_epsilon } } @@ -271,20 +225,30 @@ impl Ord for f64 { impl Orderable for f64 { /// Returns `NaN` if either of the numbers are `NaN`. #[inline(always)] - fn min(&self, other: &f64) -> f64 { - if self.is_NaN() || other.is_NaN() { Float::NaN() } else { fmin(*self, *other) } + pub fn min(&self, other: &f64) -> f64 { + cond!( + (self.is_NaN()) { *self } + (other.is_NaN()) { *other } + (*self < *other) { *self } + _ { *other } + ) } /// Returns `NaN` if either of the numbers are `NaN`. #[inline(always)] - fn max(&self, other: &f64) -> f64 { - if self.is_NaN() || other.is_NaN() { Float::NaN() } else { fmax(*self, *other) } + pub fn max(&self, other: &f64) -> f64 { + cond!( + (self.is_NaN()) { *self } + (other.is_NaN()) { *other } + (*self > *other) { *self } + _ { *other } + ) } /// Returns the number constrained within the range `mn <= self <= mx`. /// If any of the numbers are `NaN` then `NaN` is returned. #[inline(always)] - fn clamp(&self, mn: &f64, mx: &f64) -> f64 { + pub fn clamp(&self, mn: &f64, mx: &f64) -> f64 { cond!( (self.is_NaN()) { *self } (!(*self <= *mx)) { *mx } @@ -296,16 +260,16 @@ impl Orderable for f64 { impl Zero for f64 { #[inline(always)] - fn zero() -> f64 { 0.0 } + pub fn zero() -> f64 { 0.0 } /// Returns true if the number is equal to either `0.0` or `-0.0` #[inline(always)] - fn is_zero(&self) -> bool { *self == 0.0 || *self == -0.0 } + pub fn is_zero(&self) -> bool { *self == 0.0 || *self == -0.0 } } impl One for f64 { #[inline(always)] - fn one() -> f64 { 1.0 } + pub fn one() -> f64 { 1.0 } } #[cfg(not(test))] @@ -337,14 +301,14 @@ impl Neg for f64 { impl Signed for f64 { /// Computes the absolute value. Returns `NaN` if the number is `NaN`. #[inline(always)] - fn abs(&self) -> f64 { abs(*self) } + pub fn abs(&self) -> f64 { delegated::abs(*self) } /// /// The positive difference of two numbers. Returns `0.0` if the number is less than or /// equal to `other`, otherwise the difference between`self` and `other` is returned. /// #[inline(always)] - fn abs_sub(&self, other: &f64) -> f64 { abs_sub(*self, *other) } + pub fn abs_sub(&self, other: &f64) -> f64 { delegated::abs_sub(*self, *other) } /// /// # Returns @@ -354,35 +318,35 @@ impl Signed for f64 { /// - `NaN` if the number is NaN /// #[inline(always)] - fn signum(&self) -> f64 { - if self.is_NaN() { NaN } else { copysign(1.0, *self) } + pub fn signum(&self) -> f64 { + if self.is_NaN() { NaN } else { delegated::copysign(1.0, *self) } } /// Returns `true` if the number is positive, including `+0.0` and `infinity` #[inline(always)] - fn is_positive(&self) -> bool { *self > 0.0 || (1.0 / *self) == infinity } + pub fn is_positive(&self) -> bool { *self > 0.0 || (1.0 / *self) == infinity } /// Returns `true` if the number is negative, including `-0.0` and `neg_infinity` #[inline(always)] - fn is_negative(&self) -> bool { *self < 0.0 || (1.0 / *self) == neg_infinity } + pub fn is_negative(&self) -> bool { *self < 0.0 || (1.0 / *self) == neg_infinity } } impl Round for f64 { /// Round half-way cases toward `neg_infinity` #[inline(always)] - fn floor(&self) -> f64 { floor(*self) } + pub fn floor(&self) -> f64 { delegated::floor(*self) } /// Round half-way cases toward `infinity` #[inline(always)] - fn ceil(&self) -> f64 { ceil(*self) } + pub fn ceil(&self) -> f64 { delegated::ceil(*self) } /// Round half-way cases away from `0.0` #[inline(always)] - fn round(&self) -> f64 { round(*self) } + pub fn round(&self) -> f64 { delegated::round(*self) } /// The integer part of the number (rounds towards `0.0`) #[inline(always)] - fn trunc(&self) -> f64 { trunc(*self) } + pub fn trunc(&self) -> f64 { delegated::trunc(*self) } /// /// The fractional part of the number, satisfying: @@ -392,57 +356,57 @@ impl Round for f64 { /// ~~~ /// #[inline(always)] - fn fract(&self) -> f64 { *self - self.trunc() } + pub fn fract(&self) -> f64 { *self - self.trunc() } } impl Fractional for f64 { /// The reciprocal (multiplicative inverse) of the number #[inline(always)] - fn recip(&self) -> f64 { 1.0 / *self } + pub fn recip(&self) -> f64 { 1.0 / *self } } impl Algebraic for f64 { #[inline(always)] - fn pow(&self, n: f64) -> f64 { pow(*self, n) } + pub fn pow(&self, n: f64) -> f64 { delegated::pow(*self, n) } #[inline(always)] - fn sqrt(&self) -> f64 { sqrt(*self) } + pub fn sqrt(&self) -> f64 { delegated::sqrt(*self) } #[inline(always)] - fn rsqrt(&self) -> f64 { self.sqrt().recip() } + pub fn rsqrt(&self) -> f64 { self.sqrt().recip() } #[inline(always)] - fn cbrt(&self) -> f64 { cbrt(*self) } + pub fn cbrt(&self) -> f64 { delegated::cbrt(*self) } #[inline(always)] - fn hypot(&self, other: f64) -> f64 { hypot(*self, other) } + pub fn hypot(&self, other: f64) -> f64 { delegated::hypot(*self, other) } } impl Trigonometric for f64 { #[inline(always)] - fn sin(&self) -> f64 { sin(*self) } + pub fn sin(&self) -> f64 { delegated::sin(*self) } #[inline(always)] - fn cos(&self) -> f64 { cos(*self) } + pub fn cos(&self) -> f64 { delegated::cos(*self) } #[inline(always)] - fn tan(&self) -> f64 { tan(*self) } + pub fn tan(&self) -> f64 { delegated::tan(*self) } #[inline(always)] - fn asin(&self) -> f64 { asin(*self) } + pub fn asin(&self) -> f64 { delegated::asin(*self) } #[inline(always)] - fn acos(&self) -> f64 { acos(*self) } + pub fn acos(&self) -> f64 { delegated::acos(*self) } #[inline(always)] - fn atan(&self) -> f64 { atan(*self) } + pub fn atan(&self) -> f64 { delegated::atan(*self) } #[inline(always)] - fn atan2(&self, other: f64) -> f64 { atan2(*self, other) } + pub fn atan2(&self, other: f64) -> f64 { delegated::atan2(*self, other) } /// Simultaneously computes the sine and cosine of the number #[inline(always)] - fn sin_cos(&self) -> (f64, f64) { + pub fn sin_cos(&self) -> (f64, f64) { (self.sin(), self.cos()) } } @@ -450,38 +414,38 @@ impl Trigonometric for f64 { impl Exponential for f64 { /// Returns the exponential of the number #[inline(always)] - fn exp(&self) -> f64 { exp(*self) } + pub fn exp(&self) -> f64 { delegated::exp(*self) } /// Returns 2 raised to the power of the number #[inline(always)] - fn exp2(&self) -> f64 { exp2(*self) } + pub fn exp2(&self) -> f64 { delegated::exp2(*self) } /// Returns the natural logarithm of the number #[inline(always)] - fn ln(&self) -> f64 { ln(*self) } + pub fn ln(&self) -> f64 { delegated::ln(*self) } /// Returns the logarithm of the number with respect to an arbitrary base #[inline(always)] - fn log(&self, base: f64) -> f64 { self.ln() / base.ln() } + pub fn log(&self, base: f64) -> f64 { self.ln() / base.ln() } /// Returns the base 2 logarithm of the number #[inline(always)] - fn log2(&self) -> f64 { log2(*self) } + pub fn log2(&self) -> f64 { delegated::log2(*self) } /// Returns the base 10 logarithm of the number #[inline(always)] - fn log10(&self) -> f64 { log10(*self) } + pub fn log10(&self) -> f64 { delegated::log10(*self) } } impl Hyperbolic for f64 { #[inline(always)] - fn sinh(&self) -> f64 { sinh(*self) } + pub fn sinh(&self) -> f64 { delegated::sinh(*self) } #[inline(always)] - fn cosh(&self) -> f64 { cosh(*self) } + pub fn cosh(&self) -> f64 { delegated::cosh(*self) } #[inline(always)] - fn tanh(&self) -> f64 { tanh(*self) } + pub fn tanh(&self) -> f64 { delegated::tanh(*self) } /// /// Inverse hyperbolic sine @@ -493,7 +457,7 @@ impl Hyperbolic for f64 { /// - `NaN` if `self` is `NaN` /// #[inline(always)] - fn asinh(&self) -> f64 { + pub fn asinh(&self) -> f64 { match *self { neg_infinity => neg_infinity, x => (x + ((x * x) + 1.0).sqrt()).ln(), @@ -510,7 +474,7 @@ impl Hyperbolic for f64 { /// - `NaN` if `self` is `NaN` or `self < 1.0` (including `neg_infinity`) /// #[inline(always)] - fn acosh(&self) -> f64 { + pub fn acosh(&self) -> f64 { match *self { x if x < 1.0 => Float::NaN(), x => (x + ((x * x) - 1.0).sqrt()).ln(), @@ -530,173 +494,228 @@ impl Hyperbolic for f64 { /// (including `infinity` and `neg_infinity`) /// #[inline(always)] - fn atanh(&self) -> f64 { + pub fn atanh(&self) -> f64 { 0.5 * ((2.0 * *self) / (1.0 - *self)).ln_1p() } } +impl Interpolate for f64 { + pub fn linear(x: f64, y: f64, t: f64) -> f64 { + t.mul_add(y - x, x) + } + + pub fn cosine(x: f64, y: f64, t: f64) -> f64 { + (0.5 * (1.0 - (t * Real::pi()).cos())).mul_add(y - x, x) + } + + pub fn smooth(x: f64, y: f64, t: f64) -> f64 { + (t * t * t.mul_add(-2.0, 3.0)).mul_add(y - x, x) + } + + pub fn barycentric(x: f64, y: f64, z: f64, t0: f64, t1: f64) -> f64 { + let t2 = 1.0 - t0 - t1; + + t0 * x + t1 * y + t2 * z + } + + pub fn hermite(x: f64, xp: f64, y: f64, yp: f64, t: f64) -> f64 { + let a0 = t.mul_add(t * t.mul_add(2.0, -3.0), 1.0); + let a1 = t * t * t.mul_add(-2.0, 3.0); + let a2 = t * t.mul_add(t * (t - 2.0), 1.0); + let a3 = t * t * (t - 1.0); + + a0 * x + a1 * y + a2 * xp + a3 * yp + } + + pub fn cubic(x: f64, y: f64, z: f64, u: f64, t: f64) -> f64 { + let a0 = -x + y - z + u; + let a1 = x - y - a0; + let a2 = z - x; + let a3 = y; + + t.mul_add(t.mul_add(t.mul_add((t * a0), a1), a2), a3) + } + + pub fn catmull_rom(x: f64, y: f64, z: f64, u: f64, t: f64) -> f64 { + let a0 = -x + 3.0 * y - 3.0 * z + u; + let a1 = 2.0 * x - 5.0 * y + 4.0 * z - u; + let a2 = -x + z; + let a3 = 2.0 * y; + + 0.5 * t.mul_add(t.mul_add(t.mul_add((t * a0), a1), a2), a3) + } +} + impl Real for f64 { /// Archimedes' constant #[inline(always)] - fn pi() -> f64 { 3.14159265358979323846264338327950288 } + pub fn pi() -> f64 { 3.14159265358979323846264338327950288 } /// 2.0 * pi #[inline(always)] - fn two_pi() -> f64 { 6.28318530717958647692528676655900576 } + pub fn two_pi() -> f64 { 6.28318530717958647692528676655900576 } /// pi / 2.0 #[inline(always)] - fn frac_pi_2() -> f64 { 1.57079632679489661923132169163975144 } + pub fn frac_pi_2() -> f64 { 1.57079632679489661923132169163975144 } /// pi / 3.0 #[inline(always)] - fn frac_pi_3() -> f64 { 1.04719755119659774615421446109316763 } + pub fn frac_pi_3() -> f64 { 1.04719755119659774615421446109316763 } /// pi / 4.0 #[inline(always)] - fn frac_pi_4() -> f64 { 0.785398163397448309615660845819875721 } + pub fn frac_pi_4() -> f64 { 0.785398163397448309615660845819875721 } /// pi / 6.0 #[inline(always)] - fn frac_pi_6() -> f64 { 0.52359877559829887307710723054658381 } + pub fn frac_pi_6() -> f64 { 0.52359877559829887307710723054658381 } /// pi / 8.0 #[inline(always)] - fn frac_pi_8() -> f64 { 0.39269908169872415480783042290993786 } + pub fn frac_pi_8() -> f64 { 0.39269908169872415480783042290993786 } /// 1.0 / pi #[inline(always)] - fn frac_1_pi() -> f64 { 0.318309886183790671537767526745028724 } + pub fn frac_1_pi() -> f64 { 0.318309886183790671537767526745028724 } /// 2.0 / pi #[inline(always)] - fn frac_2_pi() -> f64 { 0.636619772367581343075535053490057448 } + pub fn frac_2_pi() -> f64 { 0.636619772367581343075535053490057448 } /// 2.0 / sqrt(pi) #[inline(always)] - fn frac_2_sqrtpi() -> f64 { 1.12837916709551257389615890312154517 } + pub fn frac_2_sqrtpi() -> f64 { 1.12837916709551257389615890312154517 } /// sqrt(2.0) #[inline(always)] - fn sqrt2() -> f64 { 1.41421356237309504880168872420969808 } + pub fn sqrt2() -> f64 { 1.41421356237309504880168872420969808 } /// 1.0 / sqrt(2.0) #[inline(always)] - fn frac_1_sqrt2() -> f64 { 0.707106781186547524400844362104849039 } + pub fn frac_1_sqrt2() -> f64 { 0.707106781186547524400844362104849039 } /// Euler's number #[inline(always)] - fn e() -> f64 { 2.71828182845904523536028747135266250 } + pub fn e() -> f64 { 2.71828182845904523536028747135266250 } /// log2(e) #[inline(always)] - fn log2_e() -> f64 { 1.44269504088896340735992468100189214 } + pub fn log2_e() -> f64 { 1.44269504088896340735992468100189214 } /// log10(e) #[inline(always)] - fn log10_e() -> f64 { 0.434294481903251827651128918916605082 } + pub fn log10_e() -> f64 { 0.434294481903251827651128918916605082 } /// ln(2.0) #[inline(always)] - fn ln_2() -> f64 { 0.693147180559945309417232121458176568 } + pub fn ln_2() -> f64 { 0.693147180559945309417232121458176568 } /// ln(10.0) #[inline(always)] - fn ln_10() -> f64 { 2.30258509299404568401799145468436421 } + pub fn ln_10() -> f64 { 2.30258509299404568401799145468436421 } + + /// Returns the error function of the number + #[inline(always)] + pub fn erf(&self) -> f64 { delegated::erf(*self) } + + /// Returns the complementary error function of the number + #[inline(always)] + pub fn erfc(&self) -> f64 { delegated::erfc(*self) } /// Converts to degrees, assuming the number is in radians #[inline(always)] - fn to_degrees(&self) -> f64 { *self * (180.0 / Real::pi::()) } + pub fn to_degrees(&self) -> f64 { *self * (180.0 / Real::pi::()) } /// Converts to radians, assuming the number is in degrees #[inline(always)] - fn to_radians(&self) -> f64 { *self * (Real::pi::() / 180.0) } + pub fn to_radians(&self) -> f64 { *self * (Real::pi::() / 180.0) } } impl RealExt for f64 { #[inline(always)] - fn lgamma(&self) -> (int, f64) { + pub fn lgamma(&self) -> (int, f64) { let mut sign = 0; - let result = lgamma(*self, &mut sign); + let result = delegated::lgamma(*self, &mut sign); (sign as int, result) } #[inline(always)] - fn tgamma(&self) -> f64 { tgamma(*self) } + pub fn tgamma(&self) -> f64 { delegated::tgamma(*self) } #[inline(always)] - fn j0(&self) -> f64 { j0(*self) } + pub fn j0(&self) -> f64 { delegated::j0(*self) } #[inline(always)] - fn j1(&self) -> f64 { j1(*self) } + pub fn j1(&self) -> f64 { delegated::j1(*self) } #[inline(always)] - fn jn(&self, n: int) -> f64 { jn(n as c_int, *self) } + pub fn jn(&self, n: int) -> f64 { delegated::jn(n as c_int, *self) } #[inline(always)] - fn y0(&self) -> f64 { y0(*self) } + pub fn y0(&self) -> f64 { delegated::y0(*self) } #[inline(always)] - fn y1(&self) -> f64 { y1(*self) } + pub fn y1(&self) -> f64 { delegated::y1(*self) } #[inline(always)] - fn yn(&self, n: int) -> f64 { yn(n as c_int, *self) } + pub fn yn(&self, n: int) -> f64 { delegated::yn(n as c_int, *self) } } impl Bounded for f64 { #[inline(always)] - fn min_value() -> f64 { 2.2250738585072014e-308 } + pub fn min_value() -> f64 { 2.2250738585072014e-308 } #[inline(always)] - fn max_value() -> f64 { 1.7976931348623157e+308 } + pub fn max_value() -> f64 { 1.7976931348623157e+308 } } impl Primitive for f64 { #[inline(always)] - fn bits() -> uint { 64 } + pub fn bits() -> uint { 64 } #[inline(always)] - fn bytes() -> uint { Primitive::bits::() / 8 } + pub fn bytes() -> uint { Primitive::bits::() / 8 } } impl Float for f64 { #[inline(always)] - fn NaN() -> f64 { 0.0 / 0.0 } + pub fn NaN() -> f64 { 0.0 / 0.0 } #[inline(always)] - fn infinity() -> f64 { 1.0 / 0.0 } + pub fn infinity() -> f64 { 1.0 / 0.0 } #[inline(always)] - fn neg_infinity() -> f64 { -1.0 / 0.0 } + pub fn neg_infinity() -> f64 { -1.0 / 0.0 } #[inline(always)] - fn neg_zero() -> f64 { -0.0 } + pub fn neg_zero() -> f64 { -0.0 } /// Returns `true` if the number is NaN #[inline(always)] - fn is_NaN(&self) -> bool { *self != *self } + pub fn is_NaN(&self) -> bool { *self != *self } /// Returns `true` if the number is infinite #[inline(always)] - fn is_infinite(&self) -> bool { + pub fn is_infinite(&self) -> bool { *self == Float::infinity() || *self == Float::neg_infinity() } /// Returns `true` if the number is neither infinite or NaN #[inline(always)] - fn is_finite(&self) -> bool { + pub fn is_finite(&self) -> bool { !(self.is_NaN() || self.is_infinite()) } /// Returns `true` if the number is neither zero, infinite, subnormal or NaN #[inline(always)] - fn is_normal(&self) -> bool { + pub fn is_normal(&self) -> bool { self.classify() == FPNormal } /// Returns the floating point category of the number. If only one property is going to /// be tested, it is generally faster to use the specific predicate instead. - fn classify(&self) -> FPCategory { + pub fn classify(&self) -> FPCategory { static EXP_MASK: u64 = 0x7ff0000000000000; static MAN_MASK: u64 = 0x000fffffffffffff; @@ -713,30 +732,30 @@ impl Float for f64 { } #[inline(always)] - fn mantissa_digits() -> uint { 53 } + pub fn mantissa_digits() -> uint { 53 } #[inline(always)] - fn digits() -> uint { 15 } + pub fn digits() -> uint { 15 } #[inline(always)] - fn epsilon() -> f64 { 2.2204460492503131e-16 } + pub fn epsilon() -> f64 { 2.2204460492503131e-16 } #[inline(always)] - fn min_exp() -> int { -1021 } + pub fn min_exp() -> int { -1021 } #[inline(always)] - fn max_exp() -> int { 1024 } + pub fn max_exp() -> int { 1024 } #[inline(always)] - fn min_10_exp() -> int { -307 } + pub fn min_10_exp() -> int { -307 } #[inline(always)] - fn max_10_exp() -> int { 308 } + pub fn max_10_exp() -> int { 308 } /// Constructs a floating point number by multiplying `x` by 2 raised to the power of `exp` #[inline(always)] - fn ldexp(x: f64, exp: int) -> f64 { - ldexp(x, exp as c_int) + pub fn ldexp(x: f64, exp: int) -> f64 { + delegated::ldexp(x, exp as c_int) } /// @@ -746,9 +765,9 @@ impl Float for f64 { /// - `0.5 <= abs(x) < 1.0` /// #[inline(always)] - fn frexp(&self) -> (f64, int) { + pub fn frexp(&self) -> (f64, int) { let mut exp = 0; - let x = frexp(*self, &mut exp); + let x = delegated::frexp(*self, &mut exp); (x, exp as int) } @@ -757,14 +776,14 @@ impl Float for f64 { /// even if the number is close to zero /// #[inline(always)] - fn exp_m1(&self) -> f64 { exp_m1(*self) } + pub fn exp_m1(&self) -> f64 { delegated::exp_m1(*self) } /// /// Returns the natural logarithm of the number plus `1` (`ln(1+n)`) more accurately /// than if the operations were performed separately /// #[inline(always)] - fn ln_1p(&self) -> f64 { ln_1p(*self) } + pub fn ln_1p(&self) -> f64 { delegated::ln_1p(*self) } /// /// Fused multiply-add. Computes `(self * a) + b` with only one rounding error. This @@ -772,14 +791,14 @@ impl Float for f64 { /// operation followed by an add. /// #[inline(always)] - fn mul_add(&self, a: f64, b: f64) -> f64 { - mul_add(*self, a, b) + pub fn mul_add(&self, a: f64, b: f64) -> f64 { + delegated::mul_add(*self, a, b) } /// Returns the next representable floating-point value in the direction of `other` #[inline(always)] - fn next_after(&self, other: f64) -> f64 { - next_after(*self, other) + pub fn next_after(&self, other: f64) -> f64 { + delegated::next_after(*self, other) } } @@ -892,7 +911,7 @@ impl to_str::ToStr for f64 { impl num::ToStrRadix for f64 { #[inline(always)] - fn to_str_radix(&self, rdx: uint) -> ~str { + pub fn to_str_radix(&self, rdx: uint) -> ~str { to_str_radix(*self, rdx) } } @@ -995,7 +1014,7 @@ impl FromStr for f64 { impl num::FromStrRadix for f64 { #[inline(always)] - fn from_str_radix(val: &str, rdx: uint) -> Option { + pub fn from_str_radix(val: &str, rdx: uint) -> Option { from_str_radix(val, rdx) } } @@ -1147,6 +1166,192 @@ mod tests { assert_approx_eq!((-0.5f64).atanh(), -0.54930614433405484569762261846126285f64); } + #[test] + fn test_linear() { + assert_eq!(Interpolate::linear(3.0f64, 5.0f64, 0.0f64), 3.0f64); + assert_eq!(Interpolate::linear(3.0f64, 5.0f64, 0.5f64), 4.0f64); + assert_eq!(Interpolate::linear(3.0f64, 5.0f64, 1.0f64), 5.0f64); + + assert_eq!(Interpolate::linear(3.0f64, 5.0f64, infinity), infinity); + assert_eq!(Interpolate::linear(3.0f64, 5.0f64, -infinity), -infinity); + + assert_eq!(Interpolate::linear(3.0f64, infinity, 0.5f64), infinity); + assert_eq!(Interpolate::linear(3.0f64, -infinity, 0.5f64), -infinity); + + assert!(Interpolate::linear( infinity, 5.0f64, 0.5f64).is_NaN()); + assert!(Interpolate::linear(-infinity, 5.0f64, 0.5f64).is_NaN()); + + assert!(Interpolate::linear( infinity, 5.0f64, 1.0f64).is_NaN()); + assert!(Interpolate::linear(-infinity, 5.0f64, 1.0f64).is_NaN()); + + assert!(Interpolate::linear(NaN, 5.0f64, 1.0f64).is_NaN()); + assert!(Interpolate::linear(3.0f64, NaN, 1.0f64).is_NaN()); + assert!(Interpolate::linear(3.0f64, 5.0f64, NaN).is_NaN()); + } + + #[test] + fn test_cosine() { + assert_eq!(Interpolate::cosine(3.0f64, 5.0f64, 0.0f64), 3.0f64); + assert_eq!(Interpolate::cosine(3.0f64, 5.0f64, 0.5f64), 4.0f64); + assert_eq!(Interpolate::cosine(3.0f64, 5.0f64, 1.0f64), 5.0f64); + + assert!(Interpolate::cosine(3.0f64, 5.0f64, infinity).is_NaN()); + assert!(Interpolate::cosine(3.0f64, 5.0f64, -infinity).is_NaN()); + + assert_eq!(Interpolate::cosine(3.0f64, infinity, 0.5f64), infinity); + assert_eq!(Interpolate::cosine(3.0f64, -infinity, 0.5f64), -infinity); + + assert!(Interpolate::cosine( infinity, 5.0f64, 0.5f64).is_NaN()); + assert!(Interpolate::cosine(-infinity, 5.0f64, 0.5f64).is_NaN()); + + assert!(Interpolate::cosine( infinity, 5.0f64, 1.0f64).is_NaN()); + assert!(Interpolate::cosine(-infinity, 5.0f64, 1.0f64).is_NaN()); + + assert!(Interpolate::cosine(NaN, 5.0f64, 1.0f64).is_NaN()); + assert!(Interpolate::cosine(3.0f64, NaN, 1.0f64).is_NaN()); + assert!(Interpolate::cosine(3.0f64, 5.0f64, NaN).is_NaN()); + } + + #[test] + fn test_smooth() { + assert_eq!(Interpolate::smooth(3.0f64, 5.0f64, 0.0f64), 3.0f64); + assert_eq!(Interpolate::smooth(3.0f64, 5.0f64, 0.5f64), 4.0f64); + assert_eq!(Interpolate::smooth(3.0f64, 5.0f64, 1.0f64), 5.0f64); + + assert_eq!(Interpolate::smooth(3.0f64, 5.0f64, infinity), -infinity); + assert_eq!(Interpolate::smooth(3.0f64, 5.0f64, -infinity), infinity); + + assert_eq!(Interpolate::smooth(3.0f64, infinity, 0.5f64), infinity); + assert_eq!(Interpolate::smooth(3.0f64, -infinity, 0.5f64), -infinity); + + assert!(Interpolate::smooth( infinity, 5.0f64, 0.5f64).is_NaN()); + assert!(Interpolate::smooth(-infinity, 5.0f64, 0.5f64).is_NaN()); + + assert!(Interpolate::smooth( infinity, 5.0f64, 1.0f64).is_NaN()); + assert!(Interpolate::smooth(-infinity, 5.0f64, 1.0f64).is_NaN()); + + assert!(Interpolate::smooth(NaN, 5.0f64, 1.0f64).is_NaN()); + assert!(Interpolate::smooth(3.0f64, NaN, 1.0f64).is_NaN()); + assert!(Interpolate::smooth(3.0f64, 5.0f64, NaN).is_NaN()); + } + + #[test] + fn test_barycentric() { + assert_eq!(Interpolate::barycentric(3.00f64, 0.50f64, 1.00f64, 0.00f64, 0.00f64), 1.00f64); + assert_eq!(Interpolate::barycentric(3.00f64, 0.50f64, 1.00f64, 1.00f64, 0.00f64), 3.00f64); + assert_eq!(Interpolate::barycentric(3.00f64, 0.50f64, 1.00f64, 0.00f64, 1.00f64), 0.50f64); + assert_eq!(Interpolate::barycentric(3.00f64, 0.50f64, 1.00f64, 0.50f64, 0.50f64), 1.75f64); + assert_eq!(Interpolate::barycentric(3.00f64, 0.50f64, 1.00f64, 0.00f64, 0.50f64), 0.75f64); + assert_eq!(Interpolate::barycentric(3.00f64, 0.50f64, 1.00f64, 0.50f64, 0.00f64), 2.00f64); + assert_eq!(Interpolate::barycentric(1.25f64, 2.50f64, 5.00f64, 0.40f64, 0.40f64), 2.50f64); + + assert_eq!(Interpolate::barycentric(infinity, 4.0f64, 6.0f64, 0.2f64, 0.1f64), infinity); + assert_eq!(Interpolate::barycentric(1.0f64, infinity, 6.0f64, 0.2f64, 0.1f64), infinity); + assert_eq!(Interpolate::barycentric(1.0f64, 4.0f64, infinity, 0.2f64, 0.1f64), infinity); + assert!(Interpolate::barycentric(1.0f64, 4.0f64, 6.0f64, infinity, 0.1f64).is_NaN()); + assert!(Interpolate::barycentric(1.0f64, 4.0f64, 6.0f64, 0.2f64, infinity).is_NaN()); + + assert_eq!(Interpolate::barycentric(-infinity, 4.0f64, 6.0f64, 0.2f64, 0.1f64), -infinity); + assert_eq!(Interpolate::barycentric(1.0f64, -infinity, 6.0f64, 0.2f64, 0.1f64), -infinity); + assert_eq!(Interpolate::barycentric(1.0f64, 4.0f64, -infinity, 0.2f64, 0.1f64), -infinity); + assert!(Interpolate::barycentric(1.0f64, 4.0f64, 6.0f64, -infinity, 0.1f64).is_NaN()); + assert!(Interpolate::barycentric(1.0f64, 4.0f64, 6.0f64, 0.2f64, -infinity).is_NaN()); + + assert!(Interpolate::barycentric(NaN, 4.0f64, 6.0f64, 0.0f64, 0.0f64).is_NaN()); + assert!(Interpolate::barycentric(1.0f64, NaN, 6.0f64, 0.2f64, 0.0f64).is_NaN()); + assert!(Interpolate::barycentric(1.0f64, 4.0f64, NaN, 0.4f64, 0.0f64).is_NaN()); + assert!(Interpolate::barycentric(1.0f64, 4.0f64, 6.0f64, NaN, 0.0f64).is_NaN()); + assert!(Interpolate::barycentric(1.0f64, 4.0f64, 6.0f64, 0.4f64, NaN).is_NaN()); + } + + #[test] + fn test_hermite() { + assert_eq!(Interpolate::hermite(3.0f64, 0.0f64, 5.0f64, 0.0f64, 0.0f64), 3.0f64); + assert_eq!(Interpolate::hermite(3.0f64, 0.0f64, 5.0f64, 0.0f64, 0.5f64), 4.0f64); + assert_eq!(Interpolate::hermite(3.0f64, 0.0f64, 5.0f64, 0.0f64, 1.0f64), 5.0f64); + + assert_eq!(Interpolate::hermite(3.0f64, 1.0f64, -5.0f64, 2.0f64, infinity), infinity); + assert_eq!(Interpolate::hermite(3.0f64, -1.0f64, -5.0f64, 2.0f64, -infinity), -infinity); + + assert!(Interpolate::hermite(3.0f64, 0.0f64, 5.0f64, 0.0f64, infinity).is_NaN()); + assert!(Interpolate::hermite(3.0f64, 0.0f64, 5.0f64, 0.0f64, -infinity).is_NaN()); + + assert!(Interpolate::hermite(3.0f64, -1.0f64, 5.0f64, 2.0f64, infinity).is_NaN()); + assert!(Interpolate::hermite(3.0f64, -1.0f64, 5.0f64, 2.0f64, -infinity).is_NaN()); + + assert_eq!(Interpolate::hermite(3.0f64, 0.0f64, infinity, 0.0f64, 0.5f64), infinity); + assert_eq!(Interpolate::hermite(3.0f64, 0.0f64, -infinity, 0.0f64, 0.5f64), -infinity); + + assert!(Interpolate::hermite(3.0f64, 0.0f64, infinity, 0.0f64, 0.0f64).is_NaN()); + assert!(Interpolate::hermite(3.0f64, 0.0f64, -infinity, 0.0f64, 0.0f64).is_NaN()); + + assert_eq!(Interpolate::hermite( infinity, 0.0f64, 5.0f64, 0.0f64, 0.5f64), infinity); + assert_eq!(Interpolate::hermite(-infinity, 0.0f64, 5.0f64, 0.0f64, 0.5f64), -infinity); + + assert!(Interpolate::hermite( infinity, 0.0f64, 5.0f64, 0.0f64, 1.0f64).is_NaN()); + assert!(Interpolate::hermite(-infinity, 0.0f64, 5.0f64, 0.0f64, 1.0f64).is_NaN()); + + assert!(Interpolate::hermite(NaN, 0.0f64, 5.0f64, 0.0f64, 1.0f64).is_NaN()); + assert!(Interpolate::hermite(3.0f64, NaN, 5.0f64, 0.0f64, 1.0f64).is_NaN()); + assert!(Interpolate::hermite(3.0f64, 0.0f64, NaN, 0.0f64, 1.0f64).is_NaN()); + assert!(Interpolate::hermite(3.0f64, 0.0f64, 5.0f64, NaN, 1.0f64).is_NaN()); + assert!(Interpolate::hermite(3.0f64, 0.0f64, 5.0f64, 0.0f64, NaN).is_NaN()); + } + + #[test] + fn test_cubic() { + assert_eq!(Interpolate::cubic(1.0f64, 3.0f64, 5.0f64, 6.0f64, 0.0f64), 3.0f64); + assert_eq!(Interpolate::cubic(1.0f64, 3.0f64, 5.0f64, 6.0f64, 1.0f64), 5.0f64); + + assert_eq!(Interpolate::cubic(1.0f64, 3.0f64, 5.0f64, 6.0f64, infinity), infinity); + assert_eq!(Interpolate::cubic(1.0f64, 3.0f64, 5.0f64, 6.0f64, -infinity), infinity); + + assert!(Interpolate::cubic( infinity, 3.0f64, 5.0f64, 6.0f64, 0.5f64).is_NaN()); + assert!(Interpolate::cubic(-infinity, 3.0f64, 5.0f64, 6.0f64, 0.5f64).is_NaN()); + + assert!(Interpolate::cubic(1.0f64, infinity, 5.0f64, 6.0f64, 0.5f64).is_NaN()); + assert!(Interpolate::cubic(1.0f64, -infinity, 5.0f64, 6.0f64, 0.5f64).is_NaN()); + + assert!(Interpolate::cubic(1.0f64, 3.0f64, infinity, 6.0f64, 0.5f64).is_NaN()); + assert!(Interpolate::cubic(1.0f64, 3.0f64, -infinity, 6.0f64, 0.5f64).is_NaN()); + + assert!(Interpolate::cubic(1.0f64, 3.0f64, 5.0f64, infinity, 0.5f64).is_NaN()); + assert!(Interpolate::cubic(1.0f64, 3.0f64, 5.0f64, -infinity, 0.5f64).is_NaN()); + + assert!(Interpolate::cubic( NaN, 3.0f64, 5.0f64, 6.0f64, 0.5f64).is_NaN()); + assert!(Interpolate::cubic(1.0f64, NaN, 5.0f64, 6.0f64, 0.5f64).is_NaN()); + assert!(Interpolate::cubic(1.0f64, 3.0f64, NaN, 6.0f64, 0.5f64).is_NaN()); + assert!(Interpolate::cubic(1.0f64, 3.0f64, 5.0f64, NaN, 0.5f64).is_NaN()); + assert!(Interpolate::cubic(1.0f64, 3.0f64, 5.0f64, 6.0f64, NaN).is_NaN()); + } + + #[test] + fn test_catmull_rom() { + assert_eq!(Interpolate::catmull_rom(1.0f64, 3.0f64, 5.0f64, 6.0f64, 0.0f64), 3.0f64); + assert_eq!(Interpolate::catmull_rom(1.0f64, 3.0f64, 5.0f64, 6.0f64, 1.0f64), 5.0f64); + + assert_eq!(Interpolate::catmull_rom(1.0f64, 3.0f64, 5.0f64, 6.0f64, infinity), -infinity); + assert_eq!(Interpolate::catmull_rom(1.0f64, 3.0f64, 5.0f64, 6.0f64, -infinity), -infinity); + + assert!(Interpolate::catmull_rom( infinity, 3.0f64, 5.0f64, 6.0f64, 0.5f64).is_NaN()); + assert!(Interpolate::catmull_rom(-infinity, 3.0f64, 5.0f64, 6.0f64, 0.5f64).is_NaN()); + + assert!(Interpolate::catmull_rom(1.0f64, infinity, 5.0f64, 6.0f64, 0.5f64).is_NaN()); + assert!(Interpolate::catmull_rom(1.0f64, -infinity, 5.0f64, 6.0f64, 0.5f64).is_NaN()); + + assert!(Interpolate::catmull_rom(1.0f64, 3.0f64, infinity, 6.0f64, 0.5f64).is_NaN()); + assert!(Interpolate::catmull_rom(1.0f64, 3.0f64, -infinity, 6.0f64, 0.5f64).is_NaN()); + + assert!(Interpolate::catmull_rom(1.0f64, 3.0f64, 5.0f64, infinity, 0.5f64).is_NaN()); + assert!(Interpolate::catmull_rom(1.0f64, 3.0f64, 5.0f64, -infinity, 0.5f64).is_NaN()); + + assert!(Interpolate::catmull_rom(NaN, 3.0f64, 5.0f64, 6.0f64, 0.5f64).is_NaN()); + assert!(Interpolate::catmull_rom(1.0f64, NaN, 5.0f64, 6.0f64, 0.5f64).is_NaN()); + assert!(Interpolate::catmull_rom(1.0f64, 3.0f64, NaN, 6.0f64, 0.5f64).is_NaN()); + assert!(Interpolate::catmull_rom(1.0f64, 3.0f64, 5.0f64, NaN, 0.5f64).is_NaN()); + assert!(Interpolate::catmull_rom(1.0f64, 3.0f64, 5.0f64, 6.0f64, NaN).is_NaN()); + } + #[test] fn test_real_consts() { assert_approx_eq!(Real::two_pi::(), 2.0 * Real::pi::()); diff --git a/src/libstd/num/float.rs b/src/libstd/num/float.rs index 97d661d8fe2e7..fd18e54589714 100644 --- a/src/libstd/num/float.rs +++ b/src/libstd/num/float.rs @@ -22,22 +22,12 @@ #[allow(missing_doc)]; -use f64; -use libc::c_int; use num::{Zero, One, strconv}; use num::FPCategory; use num; use prelude::*; use to_str; -pub use f64::{add, sub, mul, div, rem, lt, le, eq, ne, ge, gt}; -pub use f64::{acos, asin, atan2, cbrt, ceil, copysign, cosh, floor}; -pub use f64::{erf, erfc, exp, exp_m1, exp2, abs_sub}; -pub use f64::{mul_add, fmax, fmin, next_after, frexp, hypot, ldexp}; -pub use f64::{lgamma, ln, log_radix, ln_1p, log10, log2, ilog_radix}; -pub use f64::{modf, pow, powi, round, sinh, tanh, tgamma, trunc}; -pub use f64::{j0, j1, jn, y0, y1, yn}; - pub static NaN: float = 0.0/0.0; pub static infinity: float = 1.0/0.0; @@ -197,7 +187,7 @@ impl to_str::ToStr for float { impl num::ToStrRadix for float { #[inline(always)] - fn to_str_radix(&self, radix: uint) -> ~str { + pub fn to_str_radix(&self, radix: uint) -> ~str { to_str_radix(*self, radix) } } @@ -300,7 +290,7 @@ impl FromStr for float { impl num::FromStrRadix for float { #[inline(always)] - fn from_str_radix(val: &str, radix: uint) -> Option { + pub fn from_str_radix(val: &str, radix: uint) -> Option { from_str_radix(val, radix) } } @@ -341,31 +331,6 @@ pub fn pow_with_uint(base: uint, pow: uint) -> float { return total; } -#[inline(always)] -pub fn abs(x: float) -> float { - f64::abs(x as f64) as float -} -#[inline(always)] -pub fn sqrt(x: float) -> float { - f64::sqrt(x as f64) as float -} -#[inline(always)] -pub fn atan(x: float) -> float { - f64::atan(x as f64) as float -} -#[inline(always)] -pub fn sin(x: float) -> float { - f64::sin(x as f64) as float -} -#[inline(always)] -pub fn cos(x: float) -> float { - f64::cos(x as f64) as float -} -#[inline(always)] -pub fn tan(x: float) -> float { - f64::tan(x as f64) as float -} - impl Num for float {} #[cfg(not(test))] @@ -379,15 +344,15 @@ impl Eq for float { #[cfg(not(test))] impl ApproxEq for float { #[inline(always)] - fn approx_epsilon() -> float { 1.0e-6 } + pub fn approx_epsilon() -> float { 1.0e-6 } #[inline(always)] - fn approx_eq(&self, other: &float) -> bool { + pub fn approx_eq(&self, other: &float) -> bool { self.approx_eq_eps(other, &ApproxEq::approx_epsilon::()) } #[inline(always)] - fn approx_eq_eps(&self, other: &float, approx_epsilon: &float) -> bool { + pub fn approx_eq_eps(&self, other: &float, approx_epsilon: &float) -> bool { (*self - *other).abs() < *approx_epsilon } } @@ -407,54 +372,54 @@ impl Ord for float { impl Orderable for float { /// Returns `NaN` if either of the numbers are `NaN`. #[inline(always)] - fn min(&self, other: &float) -> float { + pub fn min(&self, other: &float) -> float { (*self as f64).min(&(*other as f64)) as float } /// Returns `NaN` if either of the numbers are `NaN`. #[inline(always)] - fn max(&self, other: &float) -> float { + pub fn max(&self, other: &float) -> float { (*self as f64).max(&(*other as f64)) as float } /// Returns the number constrained within the range `mn <= self <= mx`. /// If any of the numbers are `NaN` then `NaN` is returned. #[inline(always)] - fn clamp(&self, mn: &float, mx: &float) -> float { + pub fn clamp(&self, mn: &float, mx: &float) -> float { (*self as f64).clamp(&(*mn as f64), &(*mx as f64)) as float } } impl Zero for float { #[inline(always)] - fn zero() -> float { 0.0 } + pub fn zero() -> float { 0.0 } /// Returns true if the number is equal to either `0.0` or `-0.0` #[inline(always)] - fn is_zero(&self) -> bool { *self == 0.0 || *self == -0.0 } + pub fn is_zero(&self) -> bool { *self == 0.0 || *self == -0.0 } } impl One for float { #[inline(always)] - fn one() -> float { 1.0 } + pub fn one() -> float { 1.0 } } impl Round for float { /// Round half-way cases toward `neg_infinity` #[inline(always)] - fn floor(&self) -> float { floor(*self as f64) as float } + pub fn floor(&self) -> float { (*self as f64).floor() as float } /// Round half-way cases toward `infinity` #[inline(always)] - fn ceil(&self) -> float { ceil(*self as f64) as float } + pub fn ceil(&self) -> float { (*self as f64).ceil() as float } /// Round half-way cases away from `0.0` #[inline(always)] - fn round(&self) -> float { round(*self as f64) as float } + pub fn round(&self) -> float { (*self as f64).round() as float } /// The integer part of the number (rounds towards `0.0`) #[inline(always)] - fn trunc(&self) -> float { trunc(*self as f64) as float } + pub fn trunc(&self) -> float { (*self as f64).trunc() as float } /// /// The fractional part of the number, satisfying: @@ -464,81 +429,81 @@ impl Round for float { /// ~~~ /// #[inline(always)] - fn fract(&self) -> float { *self - self.trunc() } + pub fn fract(&self) -> float { *self - self.trunc() } } impl Fractional for float { /// The reciprocal (multiplicative inverse) of the number #[inline(always)] - fn recip(&self) -> float { 1.0 / *self } + pub fn recip(&self) -> float { 1.0 / *self } } impl Algebraic for float { #[inline(always)] - fn pow(&self, n: float) -> float { + pub fn pow(&self, n: float) -> float { (*self as f64).pow(n as f64) as float } #[inline(always)] - fn sqrt(&self) -> float { + pub fn sqrt(&self) -> float { (*self as f64).sqrt() as float } #[inline(always)] - fn rsqrt(&self) -> float { + pub fn rsqrt(&self) -> float { (*self as f64).rsqrt() as float } #[inline(always)] - fn cbrt(&self) -> float { + pub fn cbrt(&self) -> float { (*self as f64).cbrt() as float } #[inline(always)] - fn hypot(&self, other: float) -> float { + pub fn hypot(&self, other: float) -> float { (*self as f64).hypot(other as f64) as float } } impl Trigonometric for float { #[inline(always)] - fn sin(&self) -> float { + pub fn sin(&self) -> float { (*self as f64).sin() as float } #[inline(always)] - fn cos(&self) -> float { + pub fn cos(&self) -> float { (*self as f64).cos() as float } #[inline(always)] - fn tan(&self) -> float { + pub fn tan(&self) -> float { (*self as f64).tan() as float } #[inline(always)] - fn asin(&self) -> float { + pub fn asin(&self) -> float { (*self as f64).asin() as float } #[inline(always)] - fn acos(&self) -> float { + pub fn acos(&self) -> float { (*self as f64).acos() as float } #[inline(always)] - fn atan(&self) -> float { + pub fn atan(&self) -> float { (*self as f64).atan() as float } #[inline(always)] - fn atan2(&self, other: float) -> float { + pub fn atan2(&self, other: float) -> float { (*self as f64).atan2(other as f64) as float } /// Simultaneously computes the sine and cosine of the number #[inline(always)] - fn sin_cos(&self) -> (float, float) { + pub fn sin_cos(&self) -> (float, float) { match (*self as f64).sin_cos() { (s, c) => (s as float, c as float) } @@ -548,54 +513,54 @@ impl Trigonometric for float { impl Exponential for float { /// Returns the exponential of the number #[inline(always)] - fn exp(&self) -> float { + pub fn exp(&self) -> float { (*self as f64).exp() as float } /// Returns 2 raised to the power of the number #[inline(always)] - fn exp2(&self) -> float { + pub fn exp2(&self) -> float { (*self as f64).exp2() as float } /// Returns the natural logarithm of the number #[inline(always)] - fn ln(&self) -> float { + pub fn ln(&self) -> float { (*self as f64).ln() as float } /// Returns the logarithm of the number with respect to an arbitrary base #[inline(always)] - fn log(&self, base: float) -> float { + pub fn log(&self, base: float) -> float { (*self as f64).log(base as f64) as float } /// Returns the base 2 logarithm of the number #[inline(always)] - fn log2(&self) -> float { + pub fn log2(&self) -> float { (*self as f64).log2() as float } /// Returns the base 10 logarithm of the number #[inline(always)] - fn log10(&self) -> float { + pub fn log10(&self) -> float { (*self as f64).log10() as float } } impl Hyperbolic for float { #[inline(always)] - fn sinh(&self) -> float { + pub fn sinh(&self) -> float { (*self as f64).sinh() as float } #[inline(always)] - fn cosh(&self) -> float { + pub fn cosh(&self) -> float { (*self as f64).cosh() as float } #[inline(always)] - fn tanh(&self) -> float { + pub fn tanh(&self) -> float { (*self as f64).tanh() as float } @@ -609,7 +574,7 @@ impl Hyperbolic for float { /// - `NaN` if `self` is `NaN` /// #[inline(always)] - fn asinh(&self) -> float { + pub fn asinh(&self) -> float { (*self as f64).asinh() as float } @@ -623,7 +588,7 @@ impl Hyperbolic for float { /// - `NaN` if `self` is `NaN` or `self < 1.0` (including `neg_infinity`) /// #[inline(always)] - fn acosh(&self) -> float { + pub fn acosh(&self) -> float { (*self as f64).acosh() as float } @@ -640,117 +605,170 @@ impl Hyperbolic for float { /// (including `infinity` and `neg_infinity`) /// #[inline(always)] - fn atanh(&self) -> float { + pub fn atanh(&self) -> float { (*self as f64).atanh() as float } } +impl Interpolate for float { + pub fn linear(x: float, y: float, t: float) -> float { + t.mul_add(y - x, x) + } + + pub fn cosine(x: float, y: float, t: float) -> float { + (0.5 * (1.0 - (t * Real::pi()).cos())).mul_add(y - x, x) + } + + pub fn smooth(x: float, y: float, t: float) -> float { + (t * t * t.mul_add(-2.0, 3.0)).mul_add(y - x, x) + } + + pub fn barycentric(x: float, y: float, z: float, t0: float, t1: float) -> float { + let t2 = 1.0 - t0 - t1; + + t0 * x + t1 * y + t2 * z + } + + pub fn hermite(x: float, xp: float, y: float, yp: float, t: float) -> float { + let a0 = t.mul_add(t * t.mul_add(2.0, -3.0), 1.0); + let a1 = t * t * t.mul_add(-2.0, 3.0); + let a2 = t * t.mul_add(t * (t - 2.0), 1.0); + let a3 = t * t * (t - 1.0); + + a0 * x + a1 * y + a2 * xp + a3 * yp + } + + pub fn cubic(x: float, y: float, z: float, u: float, t: float) -> float { + let a0 = -x + y - z + u; + let a1 = x - y - a0; + let a2 = z - x; + let a3 = y; + + t.mul_add(t.mul_add(t.mul_add((t * a0), a1), a2), a3) + } + + pub fn catmull_rom(x: float, y: float, z: float, u: float, t: float) -> float { + let a0 = -x + 3.0 * y - 3.0 * z + u; + let a1 = 2.0 * x - 5.0 * y + 4.0 * z - u; + let a2 = -x + z; + let a3 = 2.0 * y; + + 0.5 * t.mul_add(t.mul_add(t.mul_add((t * a0), a1), a2), a3) + } +} + impl Real for float { /// Archimedes' constant #[inline(always)] - fn pi() -> float { 3.14159265358979323846264338327950288 } + pub fn pi() -> float { 3.14159265358979323846264338327950288 } /// 2.0 * pi #[inline(always)] - fn two_pi() -> float { 6.28318530717958647692528676655900576 } + pub fn two_pi() -> float { 6.28318530717958647692528676655900576 } /// pi / 2.0 #[inline(always)] - fn frac_pi_2() -> float { 1.57079632679489661923132169163975144 } + pub fn frac_pi_2() -> float { 1.57079632679489661923132169163975144 } /// pi / 3.0 #[inline(always)] - fn frac_pi_3() -> float { 1.04719755119659774615421446109316763 } + pub fn frac_pi_3() -> float { 1.04719755119659774615421446109316763 } /// pi / 4.0 #[inline(always)] - fn frac_pi_4() -> float { 0.785398163397448309615660845819875721 } + pub fn frac_pi_4() -> float { 0.785398163397448309615660845819875721 } /// pi / 6.0 #[inline(always)] - fn frac_pi_6() -> float { 0.52359877559829887307710723054658381 } + pub fn frac_pi_6() -> float { 0.52359877559829887307710723054658381 } /// pi / 8.0 #[inline(always)] - fn frac_pi_8() -> float { 0.39269908169872415480783042290993786 } + pub fn frac_pi_8() -> float { 0.39269908169872415480783042290993786 } /// 1.0 / pi #[inline(always)] - fn frac_1_pi() -> float { 0.318309886183790671537767526745028724 } + pub fn frac_1_pi() -> float { 0.318309886183790671537767526745028724 } /// 2.0 / pi #[inline(always)] - fn frac_2_pi() -> float { 0.636619772367581343075535053490057448 } + pub fn frac_2_pi() -> float { 0.636619772367581343075535053490057448 } /// 2 .0/ sqrt(pi) #[inline(always)] - fn frac_2_sqrtpi() -> float { 1.12837916709551257389615890312154517 } + pub fn frac_2_sqrtpi() -> float { 1.12837916709551257389615890312154517 } /// sqrt(2.0) #[inline(always)] - fn sqrt2() -> float { 1.41421356237309504880168872420969808 } + pub fn sqrt2() -> float { 1.41421356237309504880168872420969808 } /// 1.0 / sqrt(2.0) #[inline(always)] - fn frac_1_sqrt2() -> float { 0.707106781186547524400844362104849039 } + pub fn frac_1_sqrt2() -> float { 0.707106781186547524400844362104849039 } /// Euler's number #[inline(always)] - fn e() -> float { 2.71828182845904523536028747135266250 } + pub fn e() -> float { 2.71828182845904523536028747135266250 } /// log2(e) #[inline(always)] - fn log2_e() -> float { 1.44269504088896340735992468100189214 } + pub fn log2_e() -> float { 1.44269504088896340735992468100189214 } /// log10(e) #[inline(always)] - fn log10_e() -> float { 0.434294481903251827651128918916605082 } + pub fn log10_e() -> float { 0.434294481903251827651128918916605082 } /// ln(2.0) #[inline(always)] - fn ln_2() -> float { 0.693147180559945309417232121458176568 } + pub fn ln_2() -> float { 0.693147180559945309417232121458176568 } /// ln(10.0) #[inline(always)] - fn ln_10() -> float { 2.30258509299404568401799145468436421 } + pub fn ln_10() -> float { 2.30258509299404568401799145468436421 } + + /// Returns the error function of the number + #[inline(always)] + pub fn erf(&self) -> float { (*self as f64).erf() as float } + + /// Returns the complementary error function of the number + #[inline(always)] + pub fn erfc(&self) -> float { (*self as f64).erfc() as float } /// Converts to degrees, assuming the number is in radians #[inline(always)] - fn to_degrees(&self) -> float { (*self as f64).to_degrees() as float } + pub fn to_degrees(&self) -> float { (*self as f64).to_degrees() as float } /// Converts to radians, assuming the number is in degrees #[inline(always)] - fn to_radians(&self) -> float { (*self as f64).to_radians() as float } + pub fn to_radians(&self) -> float { (*self as f64).to_radians() as float } } impl RealExt for float { #[inline(always)] - fn lgamma(&self) -> (int, float) { - let mut sign = 0; - let result = lgamma(*self as f64, &mut sign); - (sign as int, result as float) + pub fn lgamma(&self) -> (int, float) { + match (*self as f64).lgamma() { (i, f) => (i, f as float) } } #[inline(always)] - fn tgamma(&self) -> float { tgamma(*self as f64) as float } + pub fn tgamma(&self) -> float { (*self as f64).tgamma() as float } #[inline(always)] - fn j0(&self) -> float { j0(*self as f64) as float } + pub fn j0(&self) -> float { (*self as f64).j0() as float } #[inline(always)] - fn j1(&self) -> float { j1(*self as f64) as float } + pub fn j1(&self) -> float { (*self as f64).j1() as float } #[inline(always)] - fn jn(&self, n: int) -> float { jn(n as c_int, *self as f64) as float } + pub fn jn(&self, n: int) -> float { (*self as f64).jn(n) as float } #[inline(always)] - fn y0(&self) -> float { y0(*self as f64) as float } + pub fn y0(&self) -> float { (*self as f64).y0() as float } #[inline(always)] - fn y1(&self) -> float { y1(*self as f64) as float } + pub fn y1(&self) -> float { (*self as f64).y1() as float } #[inline(always)] - fn yn(&self, n: int) -> float { yn(n as c_int, *self as f64) as float } + pub fn yn(&self, n: int) -> float { (*self as f64).yn(n) as float } } #[cfg(not(test))] @@ -791,14 +809,14 @@ impl Neg for float { impl Signed for float { /// Computes the absolute value. Returns `NaN` if the number is `NaN`. #[inline(always)] - fn abs(&self) -> float { abs(*self) } + pub fn abs(&self) -> float { (*self as f64).abs() as float } /// /// The positive difference of two numbers. Returns `0.0` if the number is less than or /// equal to `other`, otherwise the difference between`self` and `other` is returned. /// #[inline(always)] - fn abs_sub(&self, other: &float) -> float { + pub fn abs_sub(&self, other: &float) -> float { (*self as f64).abs_sub(&(*other as f64)) as float } @@ -810,93 +828,93 @@ impl Signed for float { /// - `NaN` if the number is NaN /// #[inline(always)] - fn signum(&self) -> float { - if self.is_NaN() { NaN } else { f64::copysign(1.0, *self as f64) as float } + pub fn signum(&self) -> float { + if self.is_NaN() { NaN } else { (*self as f64).signum() as float } } /// Returns `true` if the number is positive, including `+0.0` and `infinity` #[inline(always)] - fn is_positive(&self) -> bool { *self > 0.0 || (1.0 / *self) == infinity } + pub fn is_positive(&self) -> bool { *self > 0.0 || (1.0 / *self) == infinity } /// Returns `true` if the number is negative, including `-0.0` and `neg_infinity` #[inline(always)] - fn is_negative(&self) -> bool { *self < 0.0 || (1.0 / *self) == neg_infinity } + pub fn is_negative(&self) -> bool { *self < 0.0 || (1.0 / *self) == neg_infinity } } impl Bounded for float { #[inline(always)] - fn min_value() -> float { Bounded::min_value::() as float } + pub fn min_value() -> float { Bounded::min_value::() as float } #[inline(always)] - fn max_value() -> float { Bounded::max_value::() as float } + pub fn max_value() -> float { Bounded::max_value::() as float } } impl Primitive for float { #[inline(always)] - fn bits() -> uint { Primitive::bits::() } + pub fn bits() -> uint { Primitive::bits::() } #[inline(always)] - fn bytes() -> uint { Primitive::bytes::() } + pub fn bytes() -> uint { Primitive::bytes::() } } impl Float for float { #[inline(always)] - fn NaN() -> float { Float::NaN::() as float } + pub fn NaN() -> float { Float::NaN::() as float } #[inline(always)] - fn infinity() -> float { Float::infinity::() as float } + pub fn infinity() -> float { Float::infinity::() as float } #[inline(always)] - fn neg_infinity() -> float { Float::neg_infinity::() as float } + pub fn neg_infinity() -> float { Float::neg_infinity::() as float } #[inline(always)] - fn neg_zero() -> float { Float::neg_zero::() as float } + pub fn neg_zero() -> float { Float::neg_zero::() as float } /// Returns `true` if the number is NaN #[inline(always)] - fn is_NaN(&self) -> bool { (*self as f64).is_NaN() } + pub fn is_NaN(&self) -> bool { (*self as f64).is_NaN() } /// Returns `true` if the number is infinite #[inline(always)] - fn is_infinite(&self) -> bool { (*self as f64).is_infinite() } + pub fn is_infinite(&self) -> bool { (*self as f64).is_infinite() } /// Returns `true` if the number is neither infinite or NaN #[inline(always)] - fn is_finite(&self) -> bool { (*self as f64).is_finite() } + pub fn is_finite(&self) -> bool { (*self as f64).is_finite() } /// Returns `true` if the number is neither zero, infinite, subnormal or NaN #[inline(always)] - fn is_normal(&self) -> bool { (*self as f64).is_normal() } + pub fn is_normal(&self) -> bool { (*self as f64).is_normal() } /// Returns the floating point category of the number. If only one property is going to /// be tested, it is generally faster to use the specific predicate instead. #[inline(always)] - fn classify(&self) -> FPCategory { (*self as f64).classify() } + pub fn classify(&self) -> FPCategory { (*self as f64).classify() } #[inline(always)] - fn mantissa_digits() -> uint { Float::mantissa_digits::() } + pub fn mantissa_digits() -> uint { Float::mantissa_digits::() } #[inline(always)] - fn digits() -> uint { Float::digits::() } + pub fn digits() -> uint { Float::digits::() } #[inline(always)] - fn epsilon() -> float { Float::epsilon::() as float } + pub fn epsilon() -> float { Float::epsilon::() as float } #[inline(always)] - fn min_exp() -> int { Float::min_exp::() } + pub fn min_exp() -> int { Float::min_exp::() } #[inline(always)] - fn max_exp() -> int { Float::max_exp::() } + pub fn max_exp() -> int { Float::max_exp::() } #[inline(always)] - fn min_10_exp() -> int { Float::min_10_exp::() } + pub fn min_10_exp() -> int { Float::min_10_exp::() } #[inline(always)] - fn max_10_exp() -> int { Float::max_10_exp::() } + pub fn max_10_exp() -> int { Float::max_10_exp::() } /// Constructs a floating point number by multiplying `x` by 2 raised to the power of `exp` #[inline(always)] - fn ldexp(x: float, exp: int) -> float { + pub fn ldexp(x: float, exp: int) -> float { Float::ldexp(x as f64, exp) as float } @@ -907,7 +925,7 @@ impl Float for float { /// - `0.5 <= abs(x) < 1.0` /// #[inline(always)] - fn frexp(&self) -> (float, int) { + pub fn frexp(&self) -> (float, int) { match (*self as f64).frexp() { (x, exp) => (x as float, exp) } @@ -918,7 +936,7 @@ impl Float for float { /// even if the number is close to zero /// #[inline(always)] - fn exp_m1(&self) -> float { + pub fn exp_m1(&self) -> float { (*self as f64).exp_m1() as float } @@ -927,7 +945,7 @@ impl Float for float { /// than if the operations were performed separately /// #[inline(always)] - fn ln_1p(&self) -> float { + pub fn ln_1p(&self) -> float { (*self as f64).ln_1p() as float } @@ -937,14 +955,14 @@ impl Float for float { /// operation followed by an add. /// #[inline(always)] - fn mul_add(&self, a: float, b: float) -> float { - mul_add(*self as f64, a as f64, b as f64) as float + pub fn mul_add(&self, a: float, b: float) -> float { + (*self as f64).mul_add(a as f64, b as f64) as float } /// Returns the next representable floating-point value in the direction of `other` #[inline(always)] - fn next_after(&self, other: float) -> float { - next_after(*self as f64, other as f64) as float + pub fn next_after(&self, other: float) -> float { + (*self as f64).next_after(other as f64) as float } } @@ -966,12 +984,16 @@ mod tests { fn test_min() { assert_eq!(1f.min(&2f), 1f); assert_eq!(2f.min(&1f), 1f); + assert!(1f.min(&Float::NaN::()).is_NaN()); + assert!(Float::NaN::().min(&1f).is_NaN()); } #[test] fn test_max() { assert_eq!(1f.max(&2f), 2f); assert_eq!(2f.max(&1f), 2f); + assert!(1f.max(&Float::NaN::()).is_NaN()); + assert!(Float::NaN::().max(&1f).is_NaN()); } #[test] @@ -1091,6 +1113,192 @@ mod tests { assert_approx_eq!((-0.5f).atanh(), -0.54930614433405484569762261846126285f); } + #[test] + fn test_linear() { + assert_eq!(Interpolate::linear(3.0, 5.0, 0.0), 3.0); + assert_eq!(Interpolate::linear(3.0, 5.0, 0.5), 4.0); + assert_eq!(Interpolate::linear(3.0, 5.0, 1.0), 5.0); + + assert_eq!(Interpolate::linear(3.0, 5.0, infinity), infinity); + assert_eq!(Interpolate::linear(3.0, 5.0, -infinity), -infinity); + + assert_eq!(Interpolate::linear(3.0, infinity, 0.5), infinity); + assert_eq!(Interpolate::linear(3.0, -infinity, 0.5), -infinity); + + assert!(Interpolate::linear( infinity, 5.0, 0.5).is_NaN()); + assert!(Interpolate::linear(-infinity, 5.0, 0.5).is_NaN()); + + assert!(Interpolate::linear( infinity, 5.0, 1.0).is_NaN()); + assert!(Interpolate::linear(-infinity, 5.0, 1.0).is_NaN()); + + assert!(Interpolate::linear(NaN, 5.0, 1.0).is_NaN()); + assert!(Interpolate::linear(3.0, NaN, 1.0).is_NaN()); + assert!(Interpolate::linear(3.0, 5.0, NaN).is_NaN()); + } + + #[test] + fn test_cosine() { + assert_eq!(Interpolate::cosine(3.0, 5.0, 0.0), 3.0); + assert_eq!(Interpolate::cosine(3.0, 5.0, 0.5), 4.0); + assert_eq!(Interpolate::cosine(3.0, 5.0, 1.0), 5.0); + + assert!(Interpolate::cosine(3.0, 5.0, infinity).is_NaN()); + assert!(Interpolate::cosine(3.0, 5.0, -infinity).is_NaN()); + + assert_eq!(Interpolate::cosine(3.0, infinity, 0.5), infinity); + assert_eq!(Interpolate::cosine(3.0, -infinity, 0.5), -infinity); + + assert!(Interpolate::cosine( infinity, 5.0, 0.5).is_NaN()); + assert!(Interpolate::cosine(-infinity, 5.0, 0.5).is_NaN()); + + assert!(Interpolate::cosine( infinity, 5.0, 1.0).is_NaN()); + assert!(Interpolate::cosine(-infinity, 5.0, 1.0).is_NaN()); + + assert!(Interpolate::cosine(NaN, 5.0, 1.0).is_NaN()); + assert!(Interpolate::cosine(3.0, NaN, 1.0).is_NaN()); + assert!(Interpolate::cosine(3.0, 5.0, NaN).is_NaN()); + } + + #[test] + fn test_smooth() { + assert_eq!(Interpolate::smooth(3.0, 5.0, 0.0), 3.0); + assert_eq!(Interpolate::smooth(3.0, 5.0, 0.5), 4.0); + assert_eq!(Interpolate::smooth(3.0, 5.0, 1.0), 5.0); + + assert_eq!(Interpolate::smooth(3.0, 5.0, infinity), -infinity); + assert_eq!(Interpolate::smooth(3.0, 5.0, -infinity), infinity); + + assert_eq!(Interpolate::smooth(3.0, infinity, 0.5), infinity); + assert_eq!(Interpolate::smooth(3.0, -infinity, 0.5), -infinity); + + assert!(Interpolate::smooth( infinity, 5.0, 0.5).is_NaN()); + assert!(Interpolate::smooth(-infinity, 5.0, 0.5).is_NaN()); + + assert!(Interpolate::smooth( infinity, 5.0, 1.0).is_NaN()); + assert!(Interpolate::smooth(-infinity, 5.0, 1.0).is_NaN()); + + assert!(Interpolate::smooth(NaN, 5.0, 1.0).is_NaN()); + assert!(Interpolate::smooth(3.0, NaN, 1.0).is_NaN()); + assert!(Interpolate::smooth(3.0, 5.0, NaN).is_NaN()); + } + + #[test] + fn test_barycentric() { + assert_eq!(Interpolate::barycentric(3.00, 0.50, 1.00, 0.00, 0.00), 1.00); + assert_eq!(Interpolate::barycentric(3.00, 0.50, 1.00, 1.00, 0.00), 3.00); + assert_eq!(Interpolate::barycentric(3.00, 0.50, 1.00, 0.00, 1.00), 0.50); + assert_eq!(Interpolate::barycentric(3.00, 0.50, 1.00, 0.50, 0.50), 1.75); + assert_eq!(Interpolate::barycentric(3.00, 0.50, 1.00, 0.00, 0.50), 0.75); + assert_eq!(Interpolate::barycentric(3.00, 0.50, 1.00, 0.50, 0.00), 2.00); + assert_eq!(Interpolate::barycentric(1.25, 2.50, 5.00, 0.40, 0.40), 2.50); + + assert_eq!(Interpolate::barycentric(infinity, 4.0, 6.0, 0.2, 0.1), infinity); + assert_eq!(Interpolate::barycentric(1.0, infinity, 6.0, 0.2, 0.1), infinity); + assert_eq!(Interpolate::barycentric(1.0, 4.0, infinity, 0.2, 0.1), infinity); + assert!(Interpolate::barycentric(1.0, 4.0, 6.0, infinity, 0.1).is_NaN()); + assert!(Interpolate::barycentric(1.0, 4.0, 6.0, 0.2, infinity).is_NaN()); + + assert_eq!(Interpolate::barycentric(-infinity, 4.0, 6.0, 0.2, 0.1), -infinity); + assert_eq!(Interpolate::barycentric(1.0, -infinity, 6.0, 0.2, 0.1), -infinity); + assert_eq!(Interpolate::barycentric(1.0, 4.0, -infinity, 0.2, 0.1), -infinity); + assert!(Interpolate::barycentric(1.0, 4.0, 6.0, -infinity, 0.1).is_NaN()); + assert!(Interpolate::barycentric(1.0, 4.0, 6.0, 0.2, -infinity).is_NaN()); + + assert!(Interpolate::barycentric(NaN, 4.0, 6.0, 0.0, 0.0).is_NaN()); + assert!(Interpolate::barycentric(1.0, NaN, 6.0, 0.2, 0.0).is_NaN()); + assert!(Interpolate::barycentric(1.0, 4.0, NaN, 0.4, 0.0).is_NaN()); + assert!(Interpolate::barycentric(1.0, 4.0, 6.0, NaN, 0.0).is_NaN()); + assert!(Interpolate::barycentric(1.0, 4.0, 6.0, 0.4, NaN).is_NaN()); + } + + #[test] + fn test_hermite() { + assert_eq!(Interpolate::hermite(3.0, 0.0, 5.0, 0.0, 0.0), 3.0); + assert_eq!(Interpolate::hermite(3.0, 0.0, 5.0, 0.0, 0.5), 4.0); + assert_eq!(Interpolate::hermite(3.0, 0.0, 5.0, 0.0, 1.0), 5.0); + + assert_eq!(Interpolate::hermite(3.0, 1.0, -5.0, 2.0, infinity), infinity); + assert_eq!(Interpolate::hermite(3.0, -1.0, -5.0, 2.0, -infinity), -infinity); + + assert!(Interpolate::hermite(3.0, 0.0, 5.0, 0.0, infinity).is_NaN()); + assert!(Interpolate::hermite(3.0, 0.0, 5.0, 0.0, -infinity).is_NaN()); + + assert!(Interpolate::hermite(3.0, -1.0, 5.0, 2.0, infinity).is_NaN()); + assert!(Interpolate::hermite(3.0, -1.0, 5.0, 2.0, -infinity).is_NaN()); + + assert_eq!(Interpolate::hermite(3.0, 0.0, infinity, 0.0, 0.5), infinity); + assert_eq!(Interpolate::hermite(3.0, 0.0, -infinity, 0.0, 0.5), -infinity); + + assert!(Interpolate::hermite(3.0, 0.0, infinity, 0.0, 0.0).is_NaN()); + assert!(Interpolate::hermite(3.0, 0.0, -infinity, 0.0, 0.0).is_NaN()); + + assert_eq!(Interpolate::hermite( infinity, 0.0, 5.0, 0.0, 0.5), infinity); + assert_eq!(Interpolate::hermite(-infinity, 0.0, 5.0, 0.0, 0.5), -infinity); + + assert!(Interpolate::hermite( infinity, 0.0, 5.0, 0.0, 1.0).is_NaN()); + assert!(Interpolate::hermite(-infinity, 0.0, 5.0, 0.0, 1.0).is_NaN()); + + assert!(Interpolate::hermite(NaN, 0.0, 5.0, 0.0, 1.0).is_NaN()); + assert!(Interpolate::hermite(3.0, NaN, 5.0, 0.0, 1.0).is_NaN()); + assert!(Interpolate::hermite(3.0, 0.0, NaN, 0.0, 1.0).is_NaN()); + assert!(Interpolate::hermite(3.0, 0.0, 5.0, NaN, 1.0).is_NaN()); + assert!(Interpolate::hermite(3.0, 0.0, 5.0, 0.0, NaN).is_NaN()); + } + + #[test] + fn test_cubic() { + assert_eq!(Interpolate::cubic(1.0, 3.0, 5.0, 6.0, 0.0), 3.0); + assert_eq!(Interpolate::cubic(1.0, 3.0, 5.0, 6.0, 1.0), 5.0); + + assert_eq!(Interpolate::cubic(1.0, 3.0, 5.0, 6.0, infinity), infinity); + assert_eq!(Interpolate::cubic(1.0, 3.0, 5.0, 6.0, -infinity), infinity); + + assert!(Interpolate::cubic( infinity, 3.0, 5.0, 6.0, 0.5).is_NaN()); + assert!(Interpolate::cubic(-infinity, 3.0, 5.0, 6.0, 0.5).is_NaN()); + + assert!(Interpolate::cubic(1.0, infinity, 5.0, 6.0, 0.5).is_NaN()); + assert!(Interpolate::cubic(1.0, -infinity, 5.0, 6.0, 0.5).is_NaN()); + + assert!(Interpolate::cubic(1.0, 3.0, infinity, 6.0, 0.5).is_NaN()); + assert!(Interpolate::cubic(1.0, 3.0, -infinity, 6.0, 0.5).is_NaN()); + + assert!(Interpolate::cubic(1.0, 3.0, 5.0, infinity, 0.5).is_NaN()); + assert!(Interpolate::cubic(1.0, 3.0, 5.0, -infinity, 0.5).is_NaN()); + + assert!(Interpolate::cubic( NaN, 3.0, 5.0, 6.0, 0.5).is_NaN()); + assert!(Interpolate::cubic(1.0, NaN, 5.0, 6.0, 0.5).is_NaN()); + assert!(Interpolate::cubic(1.0, 3.0, NaN, 6.0, 0.5).is_NaN()); + assert!(Interpolate::cubic(1.0, 3.0, 5.0, NaN, 0.5).is_NaN()); + assert!(Interpolate::cubic(1.0, 3.0, 5.0, 6.0, NaN).is_NaN()); + } + + #[test] + fn test_catmull_rom() { + assert_eq!(Interpolate::catmull_rom(1.0, 3.0, 5.0, 6.0, 0.0), 3.0); + assert_eq!(Interpolate::catmull_rom(1.0, 3.0, 5.0, 6.0, 1.0), 5.0); + + assert_eq!(Interpolate::catmull_rom(1.0, 3.0, 5.0, 6.0, infinity), -infinity); + assert_eq!(Interpolate::catmull_rom(1.0, 3.0, 5.0, 6.0, -infinity), -infinity); + + assert!(Interpolate::catmull_rom( infinity, 3.0, 5.0, 6.0, 0.5).is_NaN()); + assert!(Interpolate::catmull_rom(-infinity, 3.0, 5.0, 6.0, 0.5).is_NaN()); + + assert!(Interpolate::catmull_rom(1.0, infinity, 5.0, 6.0, 0.5).is_NaN()); + assert!(Interpolate::catmull_rom(1.0, -infinity, 5.0, 6.0, 0.5).is_NaN()); + + assert!(Interpolate::catmull_rom(1.0, 3.0, infinity, 6.0, 0.5).is_NaN()); + assert!(Interpolate::catmull_rom(1.0, 3.0, -infinity, 6.0, 0.5).is_NaN()); + + assert!(Interpolate::catmull_rom(1.0, 3.0, 5.0, infinity, 0.5).is_NaN()); + assert!(Interpolate::catmull_rom(1.0, 3.0, 5.0, -infinity, 0.5).is_NaN()); + + assert!(Interpolate::catmull_rom(NaN, 3.0, 5.0, 6.0, 0.5).is_NaN()); + assert!(Interpolate::catmull_rom(1.0, NaN, 5.0, 6.0, 0.5).is_NaN()); + assert!(Interpolate::catmull_rom(1.0, 3.0, NaN, 6.0, 0.5).is_NaN()); + assert!(Interpolate::catmull_rom(1.0, 3.0, 5.0, NaN, 0.5).is_NaN()); + assert!(Interpolate::catmull_rom(1.0, 3.0, 5.0, 6.0, NaN).is_NaN()); + } + #[test] fn test_real_consts() { assert_approx_eq!(Real::two_pi::(), 2f * Real::pi::()); diff --git a/src/libstd/num/i16.rs b/src/libstd/num/i16.rs index 9977247b249b5..572fe32f86a3d 100644 --- a/src/libstd/num/i16.rs +++ b/src/libstd/num/i16.rs @@ -20,13 +20,13 @@ int_module!(i16, 16) impl BitCount for i16 { /// Counts the number of bits set. Wraps LLVM's `ctpop` intrinsic. #[inline(always)] - fn population_count(&self) -> i16 { unsafe { intrinsics::ctpop16(*self) } } + pub fn population_count(&self) -> i16 { unsafe { intrinsics::ctpop16(*self) } } /// Counts the number of leading zeros. Wraps LLVM's `ctlz` intrinsic. #[inline(always)] - fn leading_zeros(&self) -> i16 { unsafe { intrinsics::ctlz16(*self) } } + pub fn leading_zeros(&self) -> i16 { unsafe { intrinsics::ctlz16(*self) } } /// Counts the number of trailing zeros. Wraps LLVM's `cttz` intrinsic. #[inline(always)] - fn trailing_zeros(&self) -> i16 { unsafe { intrinsics::cttz16(*self) } } + pub fn trailing_zeros(&self) -> i16 { unsafe { intrinsics::cttz16(*self) } } } diff --git a/src/libstd/num/i32.rs b/src/libstd/num/i32.rs index 0115f306e4e0e..386caa24f5052 100644 --- a/src/libstd/num/i32.rs +++ b/src/libstd/num/i32.rs @@ -20,13 +20,13 @@ int_module!(i32, 32) impl BitCount for i32 { /// Counts the number of bits set. Wraps LLVM's `ctpop` intrinsic. #[inline(always)] - fn population_count(&self) -> i32 { unsafe { intrinsics::ctpop32(*self) } } + pub fn population_count(&self) -> i32 { unsafe { intrinsics::ctpop32(*self) } } /// Counts the number of leading zeros. Wraps LLVM's `ctlz` intrinsic. #[inline(always)] - fn leading_zeros(&self) -> i32 { unsafe { intrinsics::ctlz32(*self) } } + pub fn leading_zeros(&self) -> i32 { unsafe { intrinsics::ctlz32(*self) } } /// Counts the number of trailing zeros. Wraps LLVM's `cttz` intrinsic. #[inline(always)] - fn trailing_zeros(&self) -> i32 { unsafe { intrinsics::cttz32(*self) } } + pub fn trailing_zeros(&self) -> i32 { unsafe { intrinsics::cttz32(*self) } } } diff --git a/src/libstd/num/i64.rs b/src/libstd/num/i64.rs index 4e280f01f2720..4f033b8cdb2bc 100644 --- a/src/libstd/num/i64.rs +++ b/src/libstd/num/i64.rs @@ -20,13 +20,13 @@ int_module!(i64, 64) impl BitCount for i64 { /// Counts the number of bits set. Wraps LLVM's `ctpop` intrinsic. #[inline(always)] - fn population_count(&self) -> i64 { unsafe { intrinsics::ctpop64(*self) } } + pub fn population_count(&self) -> i64 { unsafe { intrinsics::ctpop64(*self) } } /// Counts the number of leading zeros. Wraps LLVM's `ctlz` intrinsic. #[inline(always)] - fn leading_zeros(&self) -> i64 { unsafe { intrinsics::ctlz64(*self) } } + pub fn leading_zeros(&self) -> i64 { unsafe { intrinsics::ctlz64(*self) } } /// Counts the number of trailing zeros. Wraps LLVM's `cttz` intrinsic. #[inline(always)] - fn trailing_zeros(&self) -> i64 { unsafe { intrinsics::cttz64(*self) } } + pub fn trailing_zeros(&self) -> i64 { unsafe { intrinsics::cttz64(*self) } } } diff --git a/src/libstd/num/i8.rs b/src/libstd/num/i8.rs index 939965b969185..ae9ce1ab526eb 100644 --- a/src/libstd/num/i8.rs +++ b/src/libstd/num/i8.rs @@ -20,13 +20,13 @@ int_module!(i8, 8) impl BitCount for i8 { /// Counts the number of bits set. Wraps LLVM's `ctpop` intrinsic. #[inline(always)] - fn population_count(&self) -> i8 { unsafe { intrinsics::ctpop8(*self) } } + pub fn population_count(&self) -> i8 { unsafe { intrinsics::ctpop8(*self) } } /// Counts the number of leading zeros. Wraps LLVM's `ctlz` intrinsic. #[inline(always)] - fn leading_zeros(&self) -> i8 { unsafe { intrinsics::ctlz8(*self) } } + pub fn leading_zeros(&self) -> i8 { unsafe { intrinsics::ctlz8(*self) } } /// Counts the number of trailing zeros. Wraps LLVM's `cttz` intrinsic. #[inline(always)] - fn trailing_zeros(&self) -> i8 { unsafe { intrinsics::cttz8(*self) } } + pub fn trailing_zeros(&self) -> i8 { unsafe { intrinsics::cttz8(*self) } } } diff --git a/src/libstd/num/int.rs b/src/libstd/num/int.rs index 96ef7e9e3412c..c1b041fc0aa55 100644 --- a/src/libstd/num/int.rs +++ b/src/libstd/num/int.rs @@ -23,30 +23,30 @@ int_module!(int, super::bits) impl BitCount for int { /// Counts the number of bits set. Wraps LLVM's `ctpop` intrinsic. #[inline(always)] - fn population_count(&self) -> int { (*self as i32).population_count() as int } + pub fn population_count(&self) -> int { (*self as i32).population_count() as int } /// Counts the number of leading zeros. Wraps LLVM's `ctlz` intrinsic. #[inline(always)] - fn leading_zeros(&self) -> int { (*self as i32).leading_zeros() as int } + pub fn leading_zeros(&self) -> int { (*self as i32).leading_zeros() as int } /// Counts the number of trailing zeros. Wraps LLVM's `cttz` intrinsic. #[inline(always)] - fn trailing_zeros(&self) -> int { (*self as i32).trailing_zeros() as int } + pub fn trailing_zeros(&self) -> int { (*self as i32).trailing_zeros() as int } } #[cfg(target_word_size = "64")] impl BitCount for int { /// Counts the number of bits set. Wraps LLVM's `ctpop` intrinsic. #[inline(always)] - fn population_count(&self) -> int { (*self as i64).population_count() as int } + pub fn population_count(&self) -> int { (*self as i64).population_count() as int } /// Counts the number of leading zeros. Wraps LLVM's `ctlz` intrinsic. #[inline(always)] - fn leading_zeros(&self) -> int { (*self as i64).leading_zeros() as int } + pub fn leading_zeros(&self) -> int { (*self as i64).leading_zeros() as int } /// Counts the number of trailing zeros. Wraps LLVM's `cttz` intrinsic. #[inline(always)] - fn trailing_zeros(&self) -> int { (*self as i64).trailing_zeros() as int } + pub fn trailing_zeros(&self) -> int { (*self as i64).trailing_zeros() as int } } /// Returns `base` raised to the power of `exponent` diff --git a/src/libstd/num/int_macros.rs b/src/libstd/num/int_macros.rs index 3583e2f366ff3..ff3433bb2604e 100644 --- a/src/libstd/num/int_macros.rs +++ b/src/libstd/num/int_macros.rs @@ -18,70 +18,12 @@ use num::{ToStrRadix, FromStrRadix}; use num::{Zero, One, strconv}; use prelude::*; -pub use cmp::{min, max}; - pub static bits : uint = $bits; pub static bytes : uint = ($bits / 8); pub static min_value: $T = (-1 as $T) << (bits - 1); pub static max_value: $T = min_value - 1 as $T; -/// Calculates the sum of two numbers -#[inline(always)] -pub fn add(x: $T, y: $T) -> $T { x + y } -/// Subtracts the second number from the first -#[inline(always)] -pub fn sub(x: $T, y: $T) -> $T { x - y } -/// Multiplies two numbers together -#[inline(always)] -pub fn mul(x: $T, y: $T) -> $T { x * y } -/// Divides the first argument by the second argument (using integer division) -/// Divides the first argument by the second argument (using integer division) -#[inline(always)] -pub fn div(x: $T, y: $T) -> $T { x / y } - -/// -/// Returns the remainder of y / x. -/// -/// # Examples -/// ~~~ -/// assert!(int::rem(5 / 2) == 1); -/// ~~~ -/// -/// When faced with negative numbers, the result copies the sign of the -/// dividend. -/// -/// ~~~ -/// assert!(int::rem(2 / -3) == 2); -/// ~~~ -/// -/// ~~~ -/// assert!(int::rem(-2 / 3) == -2); -/// ~~~ -/// -/// -#[inline(always)] -pub fn rem(x: $T, y: $T) -> $T { x % y } - -/// Returns true iff `x < y` -#[inline(always)] -pub fn lt(x: $T, y: $T) -> bool { x < y } -/// Returns true iff `x <= y` -#[inline(always)] -pub fn le(x: $T, y: $T) -> bool { x <= y } -/// Returns true iff `x == y` -#[inline(always)] -pub fn eq(x: $T, y: $T) -> bool { x == y } -/// Returns true iff `x != y` -#[inline(always)] -pub fn ne(x: $T, y: $T) -> bool { x != y } -/// Returns true iff `x >= y` -#[inline(always)] -pub fn ge(x: $T, y: $T) -> bool { x >= y } -/// Returns true iff `x > y` -#[inline(always)] -pub fn gt(x: $T, y: $T) -> bool { x > y } - /// /// Iterate over the range [`lo`..`hi`) /// @@ -134,16 +76,6 @@ pub fn range_rev(hi: $T, lo: $T, it: &fn($T) -> bool) -> bool { range_step(hi, lo, -1 as $T, it) } -/// Computes the bitwise complement -#[inline(always)] -pub fn compl(i: $T) -> $T { - -1 as $T ^ i -} - -/// Computes the absolute value -#[inline(always)] -pub fn abs(i: $T) -> $T { i.abs() } - impl Num for $T {} #[cfg(not(test))] @@ -168,17 +100,17 @@ impl Eq for $T { impl Orderable for $T { #[inline(always)] - fn min(&self, other: &$T) -> $T { + pub fn min(&self, other: &$T) -> $T { if *self < *other { *self } else { *other } } #[inline(always)] - fn max(&self, other: &$T) -> $T { + pub fn max(&self, other: &$T) -> $T { if *self > *other { *self } else { *other } } #[inline(always)] - fn clamp(&self, mn: &$T, mx: &$T) -> $T { + pub fn clamp(&self, mn: &$T, mx: &$T) -> $T { if *self > *mx { *mx } else if *self < *mn { *mn } else { *self } } @@ -186,15 +118,15 @@ impl Orderable for $T { impl Zero for $T { #[inline(always)] - fn zero() -> $T { 0 } + pub fn zero() -> $T { 0 } #[inline(always)] - fn is_zero(&self) -> bool { *self == 0 } + pub fn is_zero(&self) -> bool { *self == 0 } } impl One for $T { #[inline(always)] - fn one() -> $T { 1 } + pub fn one() -> $T { 1 } } #[cfg(not(test))] @@ -275,7 +207,7 @@ impl Neg<$T> for $T { impl Signed for $T { /// Computes the absolute value #[inline(always)] - fn abs(&self) -> $T { + pub fn abs(&self) -> $T { if self.is_negative() { -*self } else { *self } } @@ -284,7 +216,7 @@ impl Signed for $T { /// equal to `other`, otherwise the difference between`self` and `other` is returned. /// #[inline(always)] - fn abs_sub(&self, other: &$T) -> $T { + pub fn abs_sub(&self, other: &$T) -> $T { if *self <= *other { 0 } else { *self - *other } } @@ -296,7 +228,7 @@ impl Signed for $T { /// - `-1` if the number is negative /// #[inline(always)] - fn signum(&self) -> $T { + pub fn signum(&self) -> $T { match *self { n if n > 0 => 1, 0 => 0, @@ -306,11 +238,11 @@ impl Signed for $T { /// Returns true if the number is positive #[inline(always)] - fn is_positive(&self) -> bool { *self > 0 } + pub fn is_positive(&self) -> bool { *self > 0 } /// Returns true if the number is negative #[inline(always)] - fn is_negative(&self) -> bool { *self < 0 } + pub fn is_negative(&self) -> bool { *self < 0 } } impl Integer for $T { @@ -332,7 +264,7 @@ impl Integer for $T { /// ~~~ /// #[inline(always)] - fn div_floor(&self, other: &$T) -> $T { + pub fn div_floor(&self, other: &$T) -> $T { // Algorithm from [Daan Leijen. _Division and Modulus for Computer Scientists_, // December 2001](http://research.microsoft.com/pubs/151917/divmodnote-letter.pdf) match self.div_rem(other) { @@ -364,7 +296,7 @@ impl Integer for $T { /// ~~~ /// #[inline(always)] - fn mod_floor(&self, other: &$T) -> $T { + pub fn mod_floor(&self, other: &$T) -> $T { // Algorithm from [Daan Leijen. _Division and Modulus for Computer Scientists_, // December 2001](http://research.microsoft.com/pubs/151917/divmodnote-letter.pdf) match *self % *other { @@ -376,7 +308,7 @@ impl Integer for $T { /// Calculates `div_floor` and `mod_floor` simultaneously #[inline(always)] - fn div_mod_floor(&self, other: &$T) -> ($T,$T) { + pub fn div_mod_floor(&self, other: &$T) -> ($T,$T) { // Algorithm from [Daan Leijen. _Division and Modulus for Computer Scientists_, // December 2001](http://research.microsoft.com/pubs/151917/divmodnote-letter.pdf) match self.div_rem(other) { @@ -388,7 +320,7 @@ impl Integer for $T { /// Calculates `div` (`\`) and `rem` (`%`) simultaneously #[inline(always)] - fn div_rem(&self, other: &$T) -> ($T,$T) { + pub fn div_rem(&self, other: &$T) -> ($T,$T) { (*self / *other, *self % *other) } @@ -398,7 +330,7 @@ impl Integer for $T { /// The result is always positive /// #[inline(always)] - fn gcd(&self, other: &$T) -> $T { + pub fn gcd(&self, other: &$T) -> $T { // Use Euclid's algorithm let mut (m, n) = (*self, *other); while m != 0 { @@ -413,21 +345,21 @@ impl Integer for $T { /// Calculates the Lowest Common Multiple (LCM) of the number and `other` /// #[inline(always)] - fn lcm(&self, other: &$T) -> $T { + pub fn lcm(&self, other: &$T) -> $T { ((*self * *other) / self.gcd(other)).abs() // should not have to recaluculate abs } /// Returns `true` if the number can be divided by `other` without leaving a remainder #[inline(always)] - fn is_multiple_of(&self, other: &$T) -> bool { *self % *other == 0 } + pub fn is_multiple_of(&self, other: &$T) -> bool { *self % *other == 0 } /// Returns `true` if the number is divisible by `2` #[inline(always)] - fn is_even(&self) -> bool { self.is_multiple_of(&2) } + pub fn is_even(&self) -> bool { self.is_multiple_of(&2) } /// Returns `true` if the number is not divisible by `2` #[inline(always)] - fn is_odd(&self) -> bool { !self.is_even() } + pub fn is_odd(&self) -> bool { !self.is_even() } } impl Bitwise for $T {} @@ -470,20 +402,20 @@ impl Not<$T> for $T { impl Bounded for $T { #[inline(always)] - fn min_value() -> $T { min_value } + pub fn min_value() -> $T { min_value } #[inline(always)] - fn max_value() -> $T { max_value } + pub fn max_value() -> $T { max_value } } impl Int for $T {} impl Primitive for $T { #[inline(always)] - fn bits() -> uint { bits } + pub fn bits() -> uint { bits } #[inline(always)] - fn bytes() -> uint { bits / 8 } + pub fn bytes() -> uint { bits / 8 } } // String conversion functions and impl str -> num @@ -518,7 +450,7 @@ impl FromStr for $T { impl FromStrRadix for $T { #[inline(always)] - fn from_str_radix(s: &str, radix: uint) -> Option<$T> { + pub fn from_str_radix(s: &str, radix: uint) -> Option<$T> { from_str_radix(s, radix) } } @@ -558,7 +490,7 @@ impl ToStr for $T { impl ToStrRadix for $T { #[inline(always)] - fn to_str_radix(&self, radix: uint) -> ~str { + pub fn to_str_radix(&self, radix: uint) -> ~str { to_str_radix(*self, radix) } } diff --git a/src/libstd/num/num.rs b/src/libstd/num/num.rs index 91631d3c9b904..42034ce4b1c26 100644 --- a/src/libstd/num/num.rs +++ b/src/libstd/num/num.rs @@ -32,8 +32,8 @@ pub trait Num: Eq + Zero + One + Rem {} pub trait IntConvertible { - fn to_int(&self) -> int; - fn from_int(n: int) -> Self; + pub fn to_int(&self) -> int; + pub fn from_int(n: int) -> Self; } pub trait Orderable: Ord { @@ -41,105 +41,113 @@ pub trait Orderable: Ord { // to encumber all implementors of Ord by requiring them to implement these functions, but at // the same time we want to be able to take advantage of the speed of the specific numeric // functions (like the `fmin` and `fmax` intrinsics). - fn min(&self, other: &Self) -> Self; - fn max(&self, other: &Self) -> Self; - fn clamp(&self, mn: &Self, mx: &Self) -> Self; + pub fn min(&self, other: &Self) -> Self; + pub fn max(&self, other: &Self) -> Self; + pub fn clamp(&self, mn: &Self, mx: &Self) -> Self; } pub trait Zero { - fn zero() -> Self; // FIXME (#5527): This should be an associated constant - fn is_zero(&self) -> bool; + pub fn zero() -> Self; // FIXME (#5527): This should be an associated constant + pub fn is_zero(&self) -> bool; } pub trait One { - fn one() -> Self; // FIXME (#5527): This should be an associated constant + pub fn one() -> Self; // FIXME (#5527): This should be an associated constant } pub trait Signed: Num + Neg { - fn abs(&self) -> Self; - fn abs_sub(&self, other: &Self) -> Self; - fn signum(&self) -> Self; + pub fn abs(&self) -> Self; + pub fn abs_sub(&self, other: &Self) -> Self; + pub fn signum(&self) -> Self; - fn is_positive(&self) -> bool; - fn is_negative(&self) -> bool; + pub fn is_positive(&self) -> bool; + pub fn is_negative(&self) -> bool; } pub trait Unsigned: Num {} -// This should be moved into the default implementation for Signed::abs -pub fn abs>(v: T) -> T { - if v < Zero::zero() { v.neg() } else { v } -} - pub trait Integer: Num + Orderable + Div + Rem { - fn div_rem(&self, other: &Self) -> (Self,Self); + pub fn div_rem(&self, other: &Self) -> (Self,Self); - fn div_floor(&self, other: &Self) -> Self; - fn mod_floor(&self, other: &Self) -> Self; - fn div_mod_floor(&self, other: &Self) -> (Self,Self); + pub fn div_floor(&self, other: &Self) -> Self; + pub fn mod_floor(&self, other: &Self) -> Self; + pub fn div_mod_floor(&self, other: &Self) -> (Self,Self); - fn gcd(&self, other: &Self) -> Self; - fn lcm(&self, other: &Self) -> Self; + pub fn gcd(&self, other: &Self) -> Self; + pub fn lcm(&self, other: &Self) -> Self; - fn is_multiple_of(&self, other: &Self) -> bool; - fn is_even(&self) -> bool; - fn is_odd(&self) -> bool; + pub fn is_multiple_of(&self, other: &Self) -> bool; + pub fn is_even(&self) -> bool; + pub fn is_odd(&self) -> bool; } pub trait Round { - fn floor(&self) -> Self; - fn ceil(&self) -> Self; - fn round(&self) -> Self; - fn trunc(&self) -> Self; - fn fract(&self) -> Self; + pub fn floor(&self) -> Self; + pub fn ceil(&self) -> Self; + pub fn round(&self) -> Self; + pub fn trunc(&self) -> Self; + pub fn fract(&self) -> Self; } pub trait Fractional: Num + Orderable + Round + Div { - fn recip(&self) -> Self; + pub fn recip(&self) -> Self; } pub trait Algebraic { - fn pow(&self, n: Self) -> Self; - fn sqrt(&self) -> Self; - fn rsqrt(&self) -> Self; - fn cbrt(&self) -> Self; - fn hypot(&self, other: Self) -> Self; + pub fn pow(&self, n: Self) -> Self; + pub fn sqrt(&self) -> Self; + pub fn rsqrt(&self) -> Self; + pub fn cbrt(&self) -> Self; + pub fn hypot(&self, other: Self) -> Self; } pub trait Trigonometric { - fn sin(&self) -> Self; - fn cos(&self) -> Self; - fn tan(&self) -> Self; - fn asin(&self) -> Self; - fn acos(&self) -> Self; - fn atan(&self) -> Self; - fn atan2(&self, other: Self) -> Self; - fn sin_cos(&self) -> (Self, Self); + pub fn sin(&self) -> Self; + pub fn cos(&self) -> Self; + pub fn tan(&self) -> Self; + pub fn asin(&self) -> Self; + pub fn acos(&self) -> Self; + pub fn atan(&self) -> Self; + pub fn atan2(&self, other: Self) -> Self; + pub fn sin_cos(&self) -> (Self, Self); } pub trait Exponential { - fn exp(&self) -> Self; - fn exp2(&self) -> Self; - fn ln(&self) -> Self; - fn log(&self, base: Self) -> Self; - fn log2(&self) -> Self; - fn log10(&self) -> Self; + pub fn exp(&self) -> Self; + pub fn exp2(&self) -> Self; + pub fn ln(&self) -> Self; + pub fn log(&self, base: Self) -> Self; + pub fn log2(&self) -> Self; + pub fn log10(&self) -> Self; } pub trait Hyperbolic: Exponential { - fn sinh(&self) -> Self; - fn cosh(&self) -> Self; - fn tanh(&self) -> Self; - fn asinh(&self) -> Self; - fn acosh(&self) -> Self; - fn atanh(&self) -> Self; + pub fn sinh(&self) -> Self; + pub fn cosh(&self) -> Self; + pub fn tanh(&self) -> Self; + pub fn asinh(&self) -> Self; + pub fn acosh(&self) -> Self; + pub fn atanh(&self) -> Self; +} + +pub trait Interpolate { + pub fn linear(x: Self, y: Self, t: Self) -> Self; + pub fn cosine(x: Self, y: Self, t: Self) -> Self; + pub fn smooth(x: Self, y: Self, t: Self) -> Self; + + pub fn barycentric(x: Self, y: Self, z: Self, t0: Self, t1: Self) -> Self; + + pub fn hermite(x: Self, xp: Self, y: Self, yp: Self, t: Self) -> Self; + + pub fn cubic(x: Self, y: Self, z: Self, u: Self, t: Self) -> Self; + pub fn catmull_rom(x: Self, y: Self, z: Self, u: Self, t: Self) -> Self; } /// @@ -152,27 +160,31 @@ pub trait Real: Signed + Hyperbolic { // Common Constants // FIXME (#5527): These should be associated constants - fn pi() -> Self; - fn two_pi() -> Self; - fn frac_pi_2() -> Self; - fn frac_pi_3() -> Self; - fn frac_pi_4() -> Self; - fn frac_pi_6() -> Self; - fn frac_pi_8() -> Self; - fn frac_1_pi() -> Self; - fn frac_2_pi() -> Self; - fn frac_2_sqrtpi() -> Self; - fn sqrt2() -> Self; - fn frac_1_sqrt2() -> Self; - fn e() -> Self; - fn log2_e() -> Self; - fn log10_e() -> Self; - fn ln_2() -> Self; - fn ln_10() -> Self; + pub fn pi() -> Self; + pub fn two_pi() -> Self; + pub fn frac_pi_2() -> Self; + pub fn frac_pi_3() -> Self; + pub fn frac_pi_4() -> Self; + pub fn frac_pi_6() -> Self; + pub fn frac_pi_8() -> Self; + pub fn frac_1_pi() -> Self; + pub fn frac_2_pi() -> Self; + pub fn frac_2_sqrtpi() -> Self; + pub fn sqrt2() -> Self; + pub fn frac_1_sqrt2() -> Self; + pub fn e() -> Self; + pub fn log2_e() -> Self; + pub fn log10_e() -> Self; + pub fn ln_2() -> Self; + pub fn ln_10() -> Self; + + // Error functions + pub fn erf(&self) -> Self; + pub fn erfc(&self) -> Self; // Angular conversions - fn to_degrees(&self) -> Self; - fn to_radians(&self) -> Self; + pub fn to_degrees(&self) -> Self; + pub fn to_radians(&self) -> Self; } /// @@ -183,16 +195,16 @@ pub trait RealExt: Real { // integer type once these are implemented // Gamma functions - fn lgamma(&self) -> (int, Self); - fn tgamma(&self) -> Self; + pub fn lgamma(&self) -> (int, Self); + pub fn tgamma(&self) -> Self; // Bessel functions - fn j0(&self) -> Self; - fn j1(&self) -> Self; - fn jn(&self, n: int) -> Self; - fn y0(&self) -> Self; - fn y1(&self) -> Self; - fn yn(&self, n: int) -> Self; + pub fn j0(&self) -> Self; + pub fn j1(&self) -> Self; + pub fn jn(&self, n: int) -> Self; + pub fn y0(&self) -> Self; + pub fn y1(&self) -> Self; + pub fn yn(&self, n: int) -> Self; } /// @@ -206,15 +218,15 @@ pub trait Bitwise: Not + Shr {} pub trait BitCount { - fn population_count(&self) -> Self; - fn leading_zeros(&self) -> Self; - fn trailing_zeros(&self) -> Self; + pub fn population_count(&self) -> Self; + pub fn leading_zeros(&self) -> Self; + pub fn trailing_zeros(&self) -> Self; } pub trait Bounded { // FIXME (#5527): These should be associated constants - fn min_value() -> Self; - fn max_value() -> Self; + pub fn min_value() -> Self; + pub fn max_value() -> Self; } /// @@ -232,8 +244,8 @@ pub trait Primitive: Num + Div + Rem { // FIXME (#5527): These should be associated constants - fn bits() -> uint; - fn bytes() -> uint; + pub fn bits() -> uint; + pub fn bytes() -> uint; } /// @@ -269,32 +281,32 @@ pub trait Float: Real + Primitive + ApproxEq { // FIXME (#5527): These should be associated constants - fn NaN() -> Self; - fn infinity() -> Self; - fn neg_infinity() -> Self; - fn neg_zero() -> Self; - - fn is_NaN(&self) -> bool; - fn is_infinite(&self) -> bool; - fn is_finite(&self) -> bool; - fn is_normal(&self) -> bool; - fn classify(&self) -> FPCategory; - - fn mantissa_digits() -> uint; - fn digits() -> uint; - fn epsilon() -> Self; - fn min_exp() -> int; - fn max_exp() -> int; - fn min_10_exp() -> int; - fn max_10_exp() -> int; - - fn ldexp(x: Self, exp: int) -> Self; - fn frexp(&self) -> (Self, int); - - fn exp_m1(&self) -> Self; - fn ln_1p(&self) -> Self; - fn mul_add(&self, a: Self, b: Self) -> Self; - fn next_after(&self, other: Self) -> Self; + pub fn NaN() -> Self; + pub fn infinity() -> Self; + pub fn neg_infinity() -> Self; + pub fn neg_zero() -> Self; + + pub fn is_NaN(&self) -> bool; + pub fn is_infinite(&self) -> bool; + pub fn is_finite(&self) -> bool; + pub fn is_normal(&self) -> bool; + pub fn classify(&self) -> FPCategory; + + pub fn mantissa_digits() -> uint; + pub fn digits() -> uint; + pub fn epsilon() -> Self; + pub fn min_exp() -> int; + pub fn max_exp() -> int; + pub fn min_10_exp() -> int; + pub fn max_10_exp() -> int; + + pub fn ldexp(x: Self, exp: int) -> Self; + pub fn frexp(&self) -> (Self, int); + + pub fn exp_m1(&self) -> Self; + pub fn ln_1p(&self) -> Self; + pub fn mul_add(&self, a: Self, b: Self) -> Self; + pub fn next_after(&self, other: Self) -> Self; } /// @@ -316,50 +328,50 @@ pub fn cast(n: T) -> U { /// An interface for casting between machine scalars /// pub trait NumCast { - fn from(n: T) -> Self; - - fn to_u8(&self) -> u8; - fn to_u16(&self) -> u16; - fn to_u32(&self) -> u32; - fn to_u64(&self) -> u64; - fn to_uint(&self) -> uint; - - fn to_i8(&self) -> i8; - fn to_i16(&self) -> i16; - fn to_i32(&self) -> i32; - fn to_i64(&self) -> i64; - fn to_int(&self) -> int; - - fn to_f32(&self) -> f32; - fn to_f64(&self) -> f64; - fn to_float(&self) -> float; + pub fn from(n: T) -> Self; + + pub fn to_u8(&self) -> u8; + pub fn to_u16(&self) -> u16; + pub fn to_u32(&self) -> u32; + pub fn to_u64(&self) -> u64; + pub fn to_uint(&self) -> uint; + + pub fn to_i8(&self) -> i8; + pub fn to_i16(&self) -> i16; + pub fn to_i32(&self) -> i32; + pub fn to_i64(&self) -> i64; + pub fn to_int(&self) -> int; + + pub fn to_f32(&self) -> f32; + pub fn to_f64(&self) -> f64; + pub fn to_float(&self) -> float; } macro_rules! impl_num_cast( ($T:ty, $conv:ident) => ( impl NumCast for $T { #[inline(always)] - fn from(n: N) -> $T { + pub fn from(n: N) -> $T { // `$conv` could be generated using `concat_idents!`, but that // macro seems to be broken at the moment n.$conv() } - #[inline(always)] fn to_u8(&self) -> u8 { *self as u8 } - #[inline(always)] fn to_u16(&self) -> u16 { *self as u16 } - #[inline(always)] fn to_u32(&self) -> u32 { *self as u32 } - #[inline(always)] fn to_u64(&self) -> u64 { *self as u64 } - #[inline(always)] fn to_uint(&self) -> uint { *self as uint } - - #[inline(always)] fn to_i8(&self) -> i8 { *self as i8 } - #[inline(always)] fn to_i16(&self) -> i16 { *self as i16 } - #[inline(always)] fn to_i32(&self) -> i32 { *self as i32 } - #[inline(always)] fn to_i64(&self) -> i64 { *self as i64 } - #[inline(always)] fn to_int(&self) -> int { *self as int } - - #[inline(always)] fn to_f32(&self) -> f32 { *self as f32 } - #[inline(always)] fn to_f64(&self) -> f64 { *self as f64 } - #[inline(always)] fn to_float(&self) -> float { *self as float } + #[inline(always)] pub fn to_u8(&self) -> u8 { *self as u8 } + #[inline(always)] pub fn to_u16(&self) -> u16 { *self as u16 } + #[inline(always)] pub fn to_u32(&self) -> u32 { *self as u32 } + #[inline(always)] pub fn to_u64(&self) -> u64 { *self as u64 } + #[inline(always)] pub fn to_uint(&self) -> uint { *self as uint } + + #[inline(always)] pub fn to_i8(&self) -> i8 { *self as i8 } + #[inline(always)] pub fn to_i16(&self) -> i16 { *self as i16 } + #[inline(always)] pub fn to_i32(&self) -> i32 { *self as i32 } + #[inline(always)] pub fn to_i64(&self) -> i64 { *self as i64 } + #[inline(always)] pub fn to_int(&self) -> int { *self as int } + + #[inline(always)] pub fn to_f32(&self) -> f32 { *self as f32 } + #[inline(always)] pub fn to_f64(&self) -> f64 { *self as f64 } + #[inline(always)] pub fn to_float(&self) -> float { *self as float } } ) ) diff --git a/src/libstd/num/strconv.rs b/src/libstd/num/strconv.rs index 30efe9a392233..f90608e0430dd 100644 --- a/src/libstd/num/strconv.rs +++ b/src/libstd/num/strconv.rs @@ -21,7 +21,6 @@ use vec; use vec::{CopyableVector, ImmutableVector}; use vec::OwnedVector; use num::{NumCast, Zero, One, cast, pow_with_uint}; -use f64; pub enum ExponentFormat { ExpNone, @@ -93,8 +92,8 @@ macro_rules! impl_NumStrConv_Floating (($t:ty) => ( #[inline(always)] fn round_to_zero(&self) -> $t { - ( if *self < 0.0 { f64::ceil(*self as f64) } - else { f64::floor(*self as f64) } + ( if *self < 0.0 { (*self as f64).ceil() } + else { (*self as f64).floor() } ) as $t } diff --git a/src/libstd/num/uint_macros.rs b/src/libstd/num/uint_macros.rs index a7aebf1f176c2..ba22850423c07 100644 --- a/src/libstd/num/uint_macros.rs +++ b/src/libstd/num/uint_macros.rs @@ -19,50 +19,12 @@ use num::{ToStrRadix, FromStrRadix}; use num::{Zero, One, strconv}; use prelude::*; -pub use cmp::{min, max}; - pub static bits : uint = $bits; pub static bytes : uint = ($bits / 8); pub static min_value: $T = 0 as $T; pub static max_value: $T = 0 as $T - 1 as $T; -/// Calculates the sum of two numbers -#[inline(always)] -pub fn add(x: $T, y: $T) -> $T { x + y } -/// Subtracts the second number from the first -#[inline(always)] -pub fn sub(x: $T, y: $T) -> $T { x - y } -/// Multiplies two numbers together -#[inline(always)] -pub fn mul(x: $T, y: $T) -> $T { x * y } -/// Divides the first argument by the second argument (using integer division) -#[inline(always)] -pub fn div(x: $T, y: $T) -> $T { x / y } -/// Calculates the integer remainder when x is divided by y (equivalent to the -/// '%' operator) -#[inline(always)] -pub fn rem(x: $T, y: $T) -> $T { x % y } - -/// Returns true iff `x < y` -#[inline(always)] -pub fn lt(x: $T, y: $T) -> bool { x < y } -/// Returns true iff `x <= y` -#[inline(always)] -pub fn le(x: $T, y: $T) -> bool { x <= y } -/// Returns true iff `x == y` -#[inline(always)] -pub fn eq(x: $T, y: $T) -> bool { x == y } -/// Returns true iff `x != y` -#[inline(always)] -pub fn ne(x: $T, y: $T) -> bool { x != y } -/// Returns true iff `x >= y` -#[inline(always)] -pub fn ge(x: $T, y: $T) -> bool { x >= y } -/// Returns true iff `x > y` -#[inline(always)] -pub fn gt(x: $T, y: $T) -> bool { x > y } - #[inline(always)] /** * Iterate through a range with a given step value. @@ -111,12 +73,6 @@ pub fn range_rev(hi: $T, lo: $T, it: &fn($T) -> bool) -> bool { range_step(hi, lo, -1 as $T_SIGNED, it) } -/// Computes the bitwise complement -#[inline(always)] -pub fn compl(i: $T) -> $T { - max_value ^ i -} - impl Num for $T {} #[cfg(not(test))] @@ -163,15 +119,15 @@ impl Orderable for $T { impl Zero for $T { #[inline(always)] - fn zero() -> $T { 0 } + pub fn zero() -> $T { 0 } #[inline(always)] - fn is_zero(&self) -> bool { *self == 0 } + pub fn is_zero(&self) -> bool { *self == 0 } } impl One for $T { #[inline(always)] - fn one() -> $T { 1 } + pub fn one() -> $T { 1 } } #[cfg(not(test))] @@ -215,27 +171,27 @@ impl Unsigned for $T {} impl Integer for $T { /// Calculates `div` (`\`) and `rem` (`%`) simultaneously #[inline(always)] - fn div_rem(&self, other: &$T) -> ($T,$T) { + pub fn div_rem(&self, other: &$T) -> ($T,$T) { (*self / *other, *self % *other) } /// Unsigned integer division. Returns the same result as `div` (`/`). #[inline(always)] - fn div_floor(&self, other: &$T) -> $T { *self / *other } + pub fn div_floor(&self, other: &$T) -> $T { *self / *other } /// Unsigned integer modulo operation. Returns the same result as `rem` (`%`). #[inline(always)] - fn mod_floor(&self, other: &$T) -> $T { *self / *other } + pub fn mod_floor(&self, other: &$T) -> $T { *self / *other } /// Calculates `div_floor` and `modulo_floor` simultaneously #[inline(always)] - fn div_mod_floor(&self, other: &$T) -> ($T,$T) { + pub fn div_mod_floor(&self, other: &$T) -> ($T,$T) { (*self / *other, *self % *other) } /// Calculates the Greatest Common Divisor (GCD) of the number and `other` #[inline(always)] - fn gcd(&self, other: &$T) -> $T { + pub fn gcd(&self, other: &$T) -> $T { // Use Euclid's algorithm let mut (m, n) = (*self, *other); while m != 0 { @@ -248,21 +204,21 @@ impl Integer for $T { /// Calculates the Lowest Common Multiple (LCM) of the number and `other` #[inline(always)] - fn lcm(&self, other: &$T) -> $T { + pub fn lcm(&self, other: &$T) -> $T { (*self * *other) / self.gcd(other) } /// Returns `true` if the number can be divided by `other` without leaving a remainder #[inline(always)] - fn is_multiple_of(&self, other: &$T) -> bool { *self % *other == 0 } + pub fn is_multiple_of(&self, other: &$T) -> bool { *self % *other == 0 } /// Returns `true` if the number is divisible by `2` #[inline(always)] - fn is_even(&self) -> bool { self.is_multiple_of(&2) } + pub fn is_even(&self) -> bool { self.is_multiple_of(&2) } /// Returns `true` if the number is not divisible by `2` #[inline(always)] - fn is_odd(&self) -> bool { !self.is_even() } + pub fn is_odd(&self) -> bool { !self.is_even() } } impl Bitwise for $T {} @@ -305,10 +261,10 @@ impl Not<$T> for $T { impl Bounded for $T { #[inline(always)] - fn min_value() -> $T { min_value } + pub fn min_value() -> $T { min_value } #[inline(always)] - fn max_value() -> $T { max_value } + pub fn max_value() -> $T { max_value } } impl Int for $T {} @@ -345,7 +301,7 @@ impl FromStr for $T { impl FromStrRadix for $T { #[inline(always)] - fn from_str_radix(s: &str, radix: uint) -> Option<$T> { + pub fn from_str_radix(s: &str, radix: uint) -> Option<$T> { from_str_radix(s, radix) } } @@ -385,35 +341,35 @@ impl ToStr for $T { impl ToStrRadix for $T { #[inline(always)] - fn to_str_radix(&self, radix: uint) -> ~str { + pub fn to_str_radix(&self, radix: uint) -> ~str { to_str_radix(*self, radix) } } impl Primitive for $T { #[inline(always)] - fn bits() -> uint { bits } + pub fn bits() -> uint { bits } #[inline(always)] - fn bytes() -> uint { bits / 8 } + pub fn bytes() -> uint { bits / 8 } } impl BitCount for $T { /// Counts the number of bits set. Wraps LLVM's `ctpop` intrinsic. #[inline(always)] - fn population_count(&self) -> $T { + pub fn population_count(&self) -> $T { (*self as $T_SIGNED).population_count() as $T } /// Counts the number of leading zeros. Wraps LLVM's `ctlz` intrinsic. #[inline(always)] - fn leading_zeros(&self) -> $T { + pub fn leading_zeros(&self) -> $T { (*self as $T_SIGNED).leading_zeros() as $T } /// Counts the number of trailing zeros. Wraps LLVM's `cttz` intrinsic. #[inline(always)] - fn trailing_zeros(&self) -> $T { + pub fn trailing_zeros(&self) -> $T { (*self as $T_SIGNED).trailing_zeros() as $T } } diff --git a/src/libstd/prelude.rs b/src/libstd/prelude.rs index 476aef3709335..7e9a5a754f365 100644 --- a/src/libstd/prelude.rs +++ b/src/libstd/prelude.rs @@ -54,7 +54,7 @@ pub use iter::{Times, FromIter}; pub use iterator::Iterator; pub use num::{Num, NumCast}; pub use num::{Orderable, Signed, Unsigned, Round}; -pub use num::{Algebraic, Trigonometric, Exponential, Hyperbolic}; +pub use num::{Algebraic, Trigonometric, Exponential, Hyperbolic, Interpolate}; pub use num::{Integer, Fractional, Real, RealExt}; pub use num::{Bitwise, BitCount, Bounded}; pub use num::{Primitive, Int, Float}; diff --git a/src/libstd/rand.rs b/src/libstd/rand.rs index 7946f7e4f13f6..58fc575a3c096 100644 --- a/src/libstd/rand.rs +++ b/src/libstd/rand.rs @@ -462,7 +462,7 @@ impl RngUtil for R { */ fn gen_int_range(&mut self, start: int, end: int) -> int { assert!(start < end); - start + int::abs(self.gen::() % (end - start)) + start + (self.gen::() % (end - start)).abs() } /** diff --git a/src/libstd/rand/distributions.rs b/src/libstd/rand/distributions.rs index f08d967cbe022..b6609f57f15a2 100644 --- a/src/libstd/rand/distributions.rs +++ b/src/libstd/rand/distributions.rs @@ -20,7 +20,6 @@ // Generating Random Variables"], but more robust. If one wanted, one // could implement VIZIGNOR the ZIGNOR paper for more speed. -use f64; use rand::{Rng,Rand}; mod ziggurat_tables; @@ -39,7 +38,7 @@ fn ziggurat(rng: &mut R, let i: uint = rng.gen::() & 0xff; let x = u * X[i]; - let test_x = if center_u {f64::abs(x)} else {x}; + let test_x = if center_u { x.abs() } else { x }; // algebraically equivalent to |u| < X[i+1]/X[i] (or u < X[i+1]/X[i]) if test_x < X[i + 1] { @@ -79,7 +78,7 @@ impl Rand for StandardNormal { fn rand(rng: &mut R) -> StandardNormal { #[inline(always)] fn pdf(x: f64) -> f64 { - f64::exp((-x*x/2.0) as f64) as f64 + (-x * x / 2.0).exp() } #[inline(always)] fn zero_case(rng: &mut R, u: f64) -> f64 { @@ -93,8 +92,8 @@ impl Rand for StandardNormal { // XXX infinities? while -2.0*y < x * x { - x = f64::ln(rng.gen()) / ziggurat_tables::ZIG_NORM_R; - y = f64::ln(rng.gen()); + x = rng.gen::().ln() / ziggurat_tables::ZIG_NORM_R; + y = rng.gen::().ln(); } if u < 0.0 {x-ziggurat_tables::ZIG_NORM_R} else {ziggurat_tables::ZIG_NORM_R-x} } @@ -127,17 +126,17 @@ impl Rand for StandardNormal { /// ~~~ pub struct Exp1(f64); -// This could be done via `-f64::ln(rng.gen::())` but that is slower. +// This could be done via `-rng.gen::().ln()` but that is slower. impl Rand for Exp1 { #[inline] fn rand(rng: &mut R) -> Exp1 { #[inline(always)] fn pdf(x: f64) -> f64 { - f64::exp(-x) + (-x).exp() } #[inline(always)] fn zero_case(rng: &mut R, _u: f64) -> f64 { - ziggurat_tables::ZIG_EXP_R - f64::ln(rng.gen()) + ziggurat_tables::ZIG_EXP_R - rng.gen::().ln() } Exp1(ziggurat(rng, false, diff --git a/src/libstd/str.rs b/src/libstd/str.rs index f9d1116499586..7c46c5b8e4859 100644 --- a/src/libstd/str.rs +++ b/src/libstd/str.rs @@ -27,6 +27,7 @@ use container::Container; use iter::Times; use iterator::{Iterator, IteratorUtil}; use libc; +use num::Orderable; use option::{None, Option, Some}; use old_iter::{BaseIter, EqIter}; use ptr; @@ -1057,7 +1058,7 @@ pub fn eq(a: &~str, b: &~str) -> bool { #[inline] fn cmp(a: &str, b: &str) -> Ordering { - let low = uint::min(a.len(), b.len()); + let low = a.len().min(&b.len()); for uint::range(0, low) |idx| { match a[idx].cmp(&b[idx]) { @@ -1092,7 +1093,7 @@ impl TotalOrd for @str { #[inline] fn lt(a: &str, b: &str) -> bool { let (a_len, b_len) = (a.len(), b.len()); - let end = uint::min(a_len, b_len); + let end = a_len.min(&b_len); let mut i = 0; while i < end { diff --git a/src/libstd/unstable/extfmt.rs b/src/libstd/unstable/extfmt.rs index 07bcf6d953c3a..0f8d98b410ac8 100644 --- a/src/libstd/unstable/extfmt.rs +++ b/src/libstd/unstable/extfmt.rs @@ -475,7 +475,6 @@ pub mod rt { use float; use str; use sys; - use int; use uint; use vec; use option::{Some, None, Option}; @@ -501,7 +500,7 @@ pub mod rt { pub fn conv_int(cv: Conv, i: int, buf: &mut ~str) { let radix = 10; let prec = get_int_precision(cv); - let s : ~str = uint_to_str_prec(int::abs(i) as uint, radix, prec); + let s : ~str = uint_to_str_prec(i.abs() as uint, radix, prec); let head = if i >= 0 { if have_flag(cv.flags, flag_sign_always) { diff --git a/src/libstd/vec.rs b/src/libstd/vec.rs index 6137b589bdbae..0b68be8fec566 100644 --- a/src/libstd/vec.rs +++ b/src/libstd/vec.rs @@ -23,6 +23,7 @@ use iterator::{Iterator, IteratorUtil}; use iter::FromIter; use kinds::Copy; use libc; +use num::Orderable; use old_iter::CopyableIter; use option::{None, Option, Some}; use ptr::to_unsafe_ptr; @@ -1031,20 +1032,24 @@ pub trait VectorVector { } impl<'self, T:Copy> VectorVector for &'self [~[T]] { - /// Flattens a vector of slices of T into a single vector of T. + /// Flattens a vector of vectors of T into a single vector of T. pub fn concat(&self) -> ~[T] { self.flat_map(|&inner| inner) } /// Concatenate a vector of vectors, placing a given separator between each. pub fn connect(&self, sep: &T) -> ~[T] { - let mut r = ~[]; - let mut first = true; - for self.each |&inner| { - if first { first = false; } else { r.push(*sep); } - r.push_all(inner); + match *self { + [ref hd,..tl] => { + let mut r = hd.to_owned(); + for tl.each |&inner| { + r.push(*sep); + r.push_all(inner); + } + r + } + [] => ~[], } - r } } @@ -1056,13 +1061,17 @@ impl<'self, T:Copy> VectorVector for &'self [&'self [T]] { /// Concatenate a vector of slices, placing a given separator between each. pub fn connect(&self, sep: &T) -> ~[T] { - let mut r = ~[]; - let mut first = true; - for self.each |&inner| { - if first { first = false; } else { r.push(*sep); } - r.push_all(inner); + match *self { + [ref hd,..tl] => { + let mut r = hd.to_owned(); + for tl.each |&inner| { + r.push(*sep); + r.push_all(inner); + } + r + } + [] => ~[], } - r } } @@ -1676,7 +1685,7 @@ impl<'self,T:Eq> Equiv<~[T]> for &'self [T] { // Lexicographical comparison fn cmp(a: &[T], b: &[T]) -> Ordering { - let low = uint::min(a.len(), b.len()); + let low = a.len().min(&b.len()); for uint::range(0, low) |idx| { match a[idx].cmp(&b[idx]) { @@ -1709,7 +1718,7 @@ impl TotalOrd for @[T] { fn lt(a: &[T], b: &[T]) -> bool { let (a_len, b_len) = (a.len(), b.len()); - let end = uint::min(a_len, b_len); + let end = a_len.min(&b_len); let mut i = 0; while i < end { @@ -2405,7 +2414,6 @@ pub mod raw { /// Operations on `[u8]` pub mod bytes { use libc; - use uint; use vec::raw; use vec; @@ -2413,7 +2421,7 @@ pub mod bytes { pub fn memcmp(a: &~[u8], b: &~[u8]) -> int { let a_len = a.len(); let b_len = b.len(); - let n = uint::min(a_len, b_len) as libc::size_t; + let n = a_len.min(&b_len) as libc::size_t; let r = unsafe { libc::memcmp(raw::to_ptr(*a) as *libc::c_void, raw::to_ptr(*b) as *libc::c_void, n) as int diff --git a/src/libsyntax/ast_util.rs b/src/libsyntax/ast_util.rs index b040397de720d..2c88ca99023dc 100644 --- a/src/libsyntax/ast_util.rs +++ b/src/libsyntax/ast_util.rs @@ -388,8 +388,8 @@ impl id_range { } pub fn add(&mut self, id: node_id) { - self.min = int::min(self.min, id); - self.max = int::max(self.max, id + 1); + self.min = self.min.min(&id); + self.max = self.max.max(&(id + 1)); } } diff --git a/src/libsyntax/parse/comments.rs b/src/libsyntax/parse/comments.rs index 360ea12ec029c..1241c124ed3e8 100644 --- a/src/libsyntax/parse/comments.rs +++ b/src/libsyntax/parse/comments.rs @@ -213,7 +213,7 @@ fn trim_whitespace_prefix_and_push_line(lines: &mut ~[~str], let len = s.len(); // FIXME #3961: Doing bytewise comparison and slicing with CharPos let col = col.to_uint(); - let s1 = if all_whitespace(s, 0, uint::min(len, col)) { + let s1 = if all_whitespace(s, 0, len.min(&col)) { if col < len { str::slice(s, col, len).to_owned() } else { ~"" } diff --git a/src/test/bench/graph500-bfs.rs b/src/test/bench/graph500-bfs.rs index dee18c8a1b3ed..eb32edba83823 100644 --- a/src/test/bench/graph500-bfs.rs +++ b/src/test/bench/graph500-bfs.rs @@ -23,7 +23,6 @@ use extra::deque::Deque; use extra::par; use std::iterator::IteratorUtil; use std::hashmap::HashSet; -use std::int::abs; use std::io; use std::os; use std::rand::RngUtil; @@ -382,7 +381,7 @@ fn validate(edges: ~[(node_id, node_id)], let status = do edges.all() |e| { let (u, v) = *e; - abs(level[u] - level[v]) <= 1 + (level[u] - level[v]).abs() <= 1 }; if !status { return status } diff --git a/src/test/bench/noise.rs b/src/test/bench/noise.rs index 25bdf7dc3feff..a5daeeda74cd0 100644 --- a/src/test/bench/noise.rs +++ b/src/test/bench/noise.rs @@ -66,8 +66,8 @@ impl Noise2DContext { origins: &mut [Vec2, ..4], x: f32, y: f32) { - let x0f = f32::floor(x); - let y0f = f32::floor(y); + let x0f = x.floor(); + let y0f = y.floor(); let x0 = x0f as int; let y0 = y0f as int; let x1 = x0 + 1; diff --git a/src/test/bench/shootout-nbody.rs b/src/test/bench/shootout-nbody.rs index f1fff7ea0ac07..33674a29c9965 100644 --- a/src/test/bench/shootout-nbody.rs +++ b/src/test/bench/shootout-nbody.rs @@ -91,7 +91,7 @@ fn advance(bodies: &mut [Planet, ..N_BODIES], dt: f64, steps: i32) { d[2] = bodies[i].x[2] - bodies[j].x[2]; let d2 = d[0]*d[0] + d[1]*d[1] + d[2]*d[2]; - let mag = dt / (d2 * f64::sqrt(d2)); + let mag = dt / (d2 * d2.sqrt()); let a_mass = bodies[i].mass; let b_mass = bodies[j].mass; @@ -125,7 +125,7 @@ fn energy(bodies: &[Planet, ..N_BODIES]) -> f64 { for range(0, 3) |k| { d[k] = bodies[i].x[k] - bodies[j].x[k]; } - let dist = f64::sqrt(d[0]*d[0] + d[1]*d[1] + d[2]*d[2]); + let dist = (d[0]*d[0] + d[1]*d[1] + d[2]*d[2]).sqrt(); e -= bodies[i].mass * bodies[j].mass / dist; } } diff --git a/src/test/bench/shootout-spectralnorm.rs b/src/test/bench/shootout-spectralnorm.rs index 7356e848ba3b2..9772a86772a9f 100644 --- a/src/test/bench/shootout-spectralnorm.rs +++ b/src/test/bench/shootout-spectralnorm.rs @@ -54,5 +54,5 @@ fn main() { mult_AtAv(v, u, tmp); } - println(fmt!("%.9f", f64::sqrt(dot(u,v) / dot(v,v)) as float)); + println(fmt!("%.9f", (dot(u,v) / dot(v,v)).sqrt() as float)); } diff --git a/src/test/run-pass/class-impl-parameterized-trait.rs b/src/test/run-pass/class-impl-parameterized-trait.rs index 09967f0ab361d..febef5ec26e7b 100644 --- a/src/test/run-pass/class-impl-parameterized-trait.rs +++ b/src/test/run-pass/class-impl-parameterized-trait.rs @@ -58,7 +58,7 @@ class cat : map { fn find(&&k:int) -> Option { Some(self.get(k)) } fn remove(&&k:int) -> Option { self.meows -= k; Some(true) } fn each(f: &fn(&&int, &&bool) -> bool) { - let mut n = int::abs(self.meows); + let mut n = self.meows.abs(); while n > 0 { if !f(n, true) { break; } n -= 1; diff --git a/src/test/run-pass/class-impl-very-parameterized-trait.rs b/src/test/run-pass/class-impl-very-parameterized-trait.rs index 88686bcdbfa35..acc8f60fde307 100644 --- a/src/test/run-pass/class-impl-very-parameterized-trait.rs +++ b/src/test/run-pass/class-impl-very-parameterized-trait.rs @@ -63,7 +63,7 @@ impl Mutable for cat { impl Map for cat { fn each<'a>(&'a self, f: &fn(&int, &'a T) -> bool) -> bool { - let mut n = int::abs(self.meows); + let mut n = self.meows.abs(); while n > 0 { if !f(&n, &self.name) { return false; } n -= 1; diff --git a/src/test/run-pass/core-export-f64-sqrt.rs b/src/test/run-pass/core-export-f64-sqrt.rs index 3a683bc7cb92c..97243b257ab8d 100644 --- a/src/test/run-pass/core-export-f64-sqrt.rs +++ b/src/test/run-pass/core-export-f64-sqrt.rs @@ -17,5 +17,5 @@ pub fn main() { let digits: uint = 10 as uint; - println(float::to_str_digits(f64::sqrt(42.0f64) as float, digits)); + println(float::to_str_digits(42.0f64.sqrt() as float, digits)); } diff --git a/src/test/run-pass/trait-inheritance-self-in-supertype.rs b/src/test/run-pass/trait-inheritance-self-in-supertype.rs index f28f8cadfd98c..4dcc2dd42b7c5 100644 --- a/src/test/run-pass/trait-inheritance-self-in-supertype.rs +++ b/src/test/run-pass/trait-inheritance-self-in-supertype.rs @@ -20,7 +20,7 @@ impl FuzzyEq for f32 { } fn fuzzy_eq_eps(&self, other: &f32, epsilon: &f32) -> bool { - f32::abs(*self - *other) < *epsilon + (*self - *other).abs() < *epsilon } } @@ -34,7 +34,7 @@ impl FuzzyEq for f64 { } fn fuzzy_eq_eps(&self, other: &f64, epsilon: &f64) -> bool { - f64::abs(*self - *other) < *epsilon + (*self - *other).abs() < *epsilon } } diff --git a/src/test/run-pass/utf8_idents.rs b/src/test/run-pass/utf8_idents.rs index 2e1bec53cee6c..7c216b685a2ef 100644 --- a/src/test/run-pass/utf8_idents.rs +++ b/src/test/run-pass/utf8_idents.rs @@ -8,13 +8,11 @@ // option. This file may not be copied, modified, or distributed // except according to those terms. -use std::float; - pub fn main() { - let ε = 0.00001; - let Π = 3.14; - let लंच = Π * Π + 1.54; - assert!(float::abs((लंच - 1.54) - (Π * Π)) < ε); + let ε = 0.00001f; + let Π = 3.14f; + let लंच = Π * Π + 1.54f; + assert!(((लंच - 1.54f) - (Π * Π)).abs() < ε); assert_eq!(საჭმელად_გემრიელი_სადილი(), 0); }