diff --git a/src/libcore/core.rc b/src/libcore/core.rc index 7bf64d5b668..5b6c40e09ef 100644 --- a/src/libcore/core.rc +++ b/src/libcore/core.rc @@ -199,7 +199,7 @@ pub use vec::{OwnedVector, OwnedCopyableVector}; pub use iter::{BaseIter, ExtendedIter, EqIter, CopyableIter}; pub use iter::{CopyableOrderedIter, CopyableNonstrictIter, Times}; -pub use num::{Num, NumCast}; +pub use num::NumCast; pub use ptr::Ptr; pub use to_str::ToStr; pub use clone::Clone; diff --git a/src/libcore/num/f32.rs b/src/libcore/num/f32.rs index eaed597dff7..d27393fe507 100644 --- a/src/libcore/num/f32.rs +++ b/src/libcore/num/f32.rs @@ -13,8 +13,9 @@ use cmath; use cmp; use libc::{c_float, c_int}; -use num; use num::NumCast; +use num; +use ops; use option::Option; use from_str; use to_str; @@ -271,21 +272,6 @@ impl f32 : cmp::Ord { pure fn gt(&self, other: &f32) -> bool { (*self) > (*other) } } -impl f32: num::Num { - #[inline(always)] - pure fn add(&self, other: &f32) -> f32 { return *self + *other; } - #[inline(always)] - pure fn sub(&self, other: &f32) -> f32 { return *self - *other; } - #[inline(always)] - pure fn mul(&self, other: &f32) -> f32 { return *self * *other; } - #[inline(always)] - pure fn div(&self, other: &f32) -> f32 { return *self / *other; } - #[inline(always)] - pure fn modulo(&self, other: &f32) -> f32 { return *self % *other; } - #[inline(always)] - pure fn neg(&self) -> f32 { return -*self; } -} - impl f32: num::Zero { #[inline(always)] static pure fn zero() -> f32 { 0.0 } @@ -320,6 +306,31 @@ pub impl f32: NumCast { #[inline(always)] pure fn to_float(&self) -> float { *self as float } } +#[cfg(notest)] +impl ops::Add for f32 { + pure fn add(&self, other: &f32) -> f32 { *self + *other } +} +#[cfg(notest)] +impl ops::Sub for f32 { + pure fn sub(&self, other: &f32) -> f32 { *self - *other } +} +#[cfg(notest)] +impl ops::Mul for f32 { + pure fn mul(&self, other: &f32) -> f32 { *self * *other } +} +#[cfg(notest)] +impl ops::Div for f32 { + pure fn div(&self, other: &f32) -> f32 { *self / *other } +} +#[cfg(notest)] +impl ops::Modulo for f32 { + pure fn modulo(&self, other: &f32) -> f32 { *self % *other } +} +#[cfg(notest)] +impl ops::Neg for f32 { + pure fn neg(&self) -> f32 { -*self } +} + #[abi="rust-intrinsic"] pub extern { fn floorf32(val: f32) -> f32; diff --git a/src/libcore/num/f64.rs b/src/libcore/num/f64.rs index 8aaa48524e2..d189a0254eb 100644 --- a/src/libcore/num/f64.rs +++ b/src/libcore/num/f64.rs @@ -14,8 +14,9 @@ use cmath; use cmp; use libc::{c_double, c_int}; use libc; -use num; use num::NumCast; +use num; +use ops; use option::Option; use to_str; use from_str; @@ -296,21 +297,6 @@ impl f64 : cmp::Ord { pure fn gt(&self, other: &f64) -> bool { (*self) > (*other) } } -impl f64: num::Num { - #[inline(always)] - pure fn add(&self, other: &f64) -> f64 { return *self + *other; } - #[inline(always)] - pure fn sub(&self, other: &f64) -> f64 { return *self - *other; } - #[inline(always)] - pure fn mul(&self, other: &f64) -> f64 { return *self * *other; } - #[inline(always)] - pure fn div(&self, other: &f64) -> f64 { return *self / *other; } - #[inline(always)] - pure fn modulo(&self, other: &f64) -> f64 { return *self % *other; } - #[inline(always)] - pure fn neg(&self) -> f64 { return -*self; } -} - pub impl f64: NumCast { /** * Cast `n` to an `f64` @@ -345,6 +331,31 @@ impl f64: num::One { static pure fn one() -> f64 { 1.0 } } +#[cfg(notest)] +impl ops::Add for f64 { + pure fn add(&self, other: &f64) -> f64 { *self + *other } +} +#[cfg(notest)] +impl ops::Sub for f64 { + pure fn sub(&self, other: &f64) -> f64 { *self - *other } +} +#[cfg(notest)] +impl ops::Mul for f64 { + pure fn mul(&self, other: &f64) -> f64 { *self * *other } +} +#[cfg(notest)] +impl ops::Div for f64 { + pure fn div(&self, other: &f64) -> f64 { *self / *other } +} +#[cfg(notest)] +impl ops::Modulo for f64 { + pure fn modulo(&self, other: &f64) -> f64 { *self % *other } +} +#[cfg(notest)] +impl ops::Neg for f64 { + pure fn neg(&self) -> f64 { -*self } +} + #[abi="rust-intrinsic"] pub extern { fn floorf64(val: f64) -> f64; diff --git a/src/libcore/num/float.rs b/src/libcore/num/float.rs index c7d391bab08..bbea58f5cf5 100644 --- a/src/libcore/num/float.rs +++ b/src/libcore/num/float.rs @@ -25,8 +25,9 @@ use m_float = f64; use cmp::{Eq, Ord}; use cmp; use f64; -use num; use num::NumCast; +use num; +use ops; use option::{None, Option, Some}; use str; use uint; @@ -404,21 +405,6 @@ impl float : Ord { pure fn gt(&self, other: &float) -> bool { (*self) > (*other) } } -impl float: num::Num { - #[inline(always)] - pub pure fn add(&self, other: &float) -> float { return *self + *other; } - #[inline(always)] - pub pure fn sub(&self, other: &float) -> float { return *self - *other; } - #[inline(always)] - pub pure fn mul(&self, other: &float) -> float { return *self * *other; } - #[inline(always)] - pub pure fn div(&self, other: &float) -> float { return *self / *other; } - #[inline(always)] - pure fn modulo(&self, other: &float) -> float { return *self % *other; } - #[inline(always)] - pure fn neg(&self) -> float { return -*self; } -} - impl float: num::Zero { #[inline(always)] static pure fn zero() -> float { 0.0 } @@ -486,6 +472,31 @@ impl float: num::Round { } } +#[cfg(notest)] +impl ops::Add for float { + pure fn add(&self, other: &float) -> float { *self + *other } +} +#[cfg(notest)] +impl ops::Sub for float { + pure fn sub(&self, other: &float) -> float { *self - *other } +} +#[cfg(notest)] +impl ops::Mul for float { + pure fn mul(&self, other: &float) -> float { *self * *other } +} +#[cfg(notest)] +impl ops::Div for float { + pure fn div(&self, other: &float) -> float { *self / *other } +} +#[cfg(notest)] +impl ops::Modulo for float { + pure fn modulo(&self, other: &float) -> float { *self % *other } +} +#[cfg(notest)] +impl ops::Neg for float { + pure fn neg(&self) -> float { -*self } +} + #[test] pub fn test_from_str() { assert from_str(~"3") == Some(3.); diff --git a/src/libcore/num/int-template.rs b/src/libcore/num/int-template.rs index 71c06bc9d24..c25938a187f 100644 --- a/src/libcore/num/int-template.rs +++ b/src/libcore/num/int-template.rs @@ -166,21 +166,6 @@ impl T : Eq { pure fn ne(&self, other: &T) -> bool { return (*self) != (*other); } } -impl T: num::Num { - #[inline(always)] - pure fn add(&self, other: &T) -> T { return *self + *other; } - #[inline(always)] - pure fn sub(&self, other: &T) -> T { return *self - *other; } - #[inline(always)] - pure fn mul(&self, other: &T) -> T { return *self * *other; } - #[inline(always)] - pure fn div(&self, other: &T) -> T { return *self / *other; } - #[inline(always)] - pure fn modulo(&self, other: &T) -> T { return *self % *other; } - #[inline(always)] - pure fn neg(&self) -> T { return -*self; } -} - impl T: num::Zero { #[inline(always)] static pure fn zero() -> T { 0 } @@ -203,6 +188,31 @@ impl T: num::Round { pure fn fract(&self) -> T { 0 } } +#[cfg(notest)] +impl ops::Add for T { + pure fn add(&self, other: &T) -> T { *self + *other } +} +#[cfg(notest)] +impl ops::Sub for T { + pure fn sub(&self, other: &T) -> T { *self - *other } +} +#[cfg(notest)] +impl ops::Mul for T { + pure fn mul(&self, other: &T) -> T { *self * *other } +} +#[cfg(notest)] +impl ops::Div for T { + pure fn div(&self, other: &T) -> T { *self / *other } +} +#[cfg(notest)] +impl ops::Modulo for T { + pure fn modulo(&self, other: &T) -> T { *self % *other } +} +#[cfg(notest)] +impl ops::Neg for T { + pure fn neg(&self) -> T { -*self } +} + // String conversion functions and impl str -> num /// Parse a string as a number in base 10. diff --git a/src/libcore/num/num.rs b/src/libcore/num/num.rs index 8435a7b8ea2..44cd66363fb 100644 --- a/src/libcore/num/num.rs +++ b/src/libcore/num/num.rs @@ -10,22 +10,13 @@ //! An interface for numeric types use core::cmp::{Ord, Eq}; +use ops::{Add, Div, Modulo, Mul, Neg, Sub}; use option::{None, Option, Some}; use char; use str; use kinds::Copy; use vec; -pub trait Num { - // FIXME: Trait composition. (#2616) - pure fn add(&self, other: &Self) -> Self; - pure fn sub(&self, other: &Self) -> Self; - pure fn mul(&self, other: &Self) -> Self; - pure fn div(&self, other: &Self) -> Self; - pure fn modulo(&self, other: &Self) -> Self; - pure fn neg(&self) -> Self; -} - pub trait IntConvertible { pure fn to_int(&self) -> int; static pure fn from_int(n: int) -> Self; @@ -39,7 +30,7 @@ pub trait One { static pure fn one() -> Self; } -pub pure fn abs(v: T) -> T { +pub pure fn abs>(v: T) -> T { if v < Zero::zero() { v.neg() } else { v } } @@ -109,7 +100,7 @@ pub trait FromStrRadix { /// Dynamically calculates the value `inf` (`1/0`). /// Can fail on integer types. #[inline(always)] -pub pure fn infinity() -> T { +pub pure fn infinity>() -> T { let _0: T = Zero::zero(); let _1: T = One::one(); _1 / _0 @@ -118,7 +109,7 @@ pub pure fn infinity() -> T { /// Dynamically calculates the value `-inf` (`-1/0`). /// Can fail on integer types. #[inline(always)] -pub pure fn neg_infinity() -> T { +pub pure fn neg_infinity+Neg>() -> T { let _0: T = Zero::zero(); let _1: T = One::one(); - _1 / _0 @@ -127,7 +118,7 @@ pub pure fn neg_infinity() -> T { /// Dynamically calculates the value `NaN` (`0/0`). /// Can fail on integer types. #[inline(always)] -pub pure fn NaN() -> T { +pub pure fn NaN>() -> T { let _0: T = Zero::zero(); _0 / _0 } @@ -135,27 +126,28 @@ pub pure fn NaN() -> T { /// Returns `true` if `num` has the value `inf` (`1/0`). /// Can fail on integer types. #[inline(always)] -pub pure fn is_infinity(num: &T) -> bool { +pub pure fn is_infinity>(num: &T) -> bool { (*num) == (infinity::()) } /// Returns `true` if `num` has the value `-inf` (`-1/0`). /// Can fail on integer types. #[inline(always)] -pub pure fn is_neg_infinity(num: &T) -> bool { +pub pure fn is_neg_infinity+Neg>(num: &T) + -> bool { (*num) == (neg_infinity::()) } /// Returns `true` if `num` has the value `NaN` (is not equal to itself). #[inline(always)] -pub pure fn is_NaN(num: &T) -> bool { +pub pure fn is_NaN(num: &T) -> bool { (*num) != (*num) } /// Returns `true` if `num` has the value `-0` (`1/num == -1/0`). /// Can fail on integer types. #[inline(always)] -pub pure fn is_neg_zero(num: &T) -> bool { +pub pure fn is_neg_zero+Neg>(num: &T) -> bool { let _1: T = One::one(); let _0: T = Zero::zero(); *num == _0 && is_neg_infinity(&(_1 / *num)) @@ -174,8 +166,8 @@ pub pure fn is_neg_zero(num: &T) -> bool { * - If code written to use this function doesn't care about it, it's * probably assuming that `x^0` always equals `1`. */ -pub pure fn pow_with_uint(radix: uint, - pow: uint) -> T { +pub pure fn pow_with_uint+Mul>( + radix: uint, pow: uint) -> T { let _0: T = Zero::zero(); let _1: T = One::one(); @@ -256,7 +248,8 @@ pub enum SignFormat { * those special values, and `special` is `false`, because then the * algorithm just does normal calculations on them. */ -pub pure fn to_str_bytes_common( +pub pure fn to_str_bytes_common+ + Neg+Modulo+Mul>( num: &T, radix: uint, special: bool, negative_zero: bool, sign: SignFormat, digits: SignificantDigits) -> (~[u8], bool) { if radix as int < 2 { @@ -478,7 +471,8 @@ pub pure fn to_str_bytes_common( * `to_str_bytes_common()`, for details see there. */ #[inline(always)] -pub pure fn to_str_common( +pub pure fn to_str_common+Neg + +Modulo+Mul>( num: &T, radix: uint, special: bool, negative_zero: bool, sign: SignFormat, digits: SignificantDigits) -> (~str, bool) { let (bytes, special) = to_str_bytes_common(num, radix, special, @@ -533,7 +527,8 @@ priv const DIGIT_E_RADIX: uint = ('e' as uint) - ('a' as uint) + 11u; * - Could accept option to allow ignoring underscores, allowing for numbers * formated like `FF_AE_FF_FF`. */ -pub pure fn from_str_bytes_common( +pub pure fn from_str_bytes_common+ + Mul+Sub+Neg+Add>( buf: &[u8], radix: uint, negative: bool, fractional: bool, special: bool, exponent: ExponentFormat, empty_zero: bool ) -> Option { @@ -720,7 +715,8 @@ pub pure fn from_str_bytes_common( * `from_str_bytes_common()`, for details see there. */ #[inline(always)] -pub pure fn from_str_common( +pub pure fn from_str_common+Mul+ + Sub+Neg+Add>( buf: &str, radix: uint, negative: bool, fractional: bool, special: bool, exponent: ExponentFormat, empty_zero: bool ) -> Option { diff --git a/src/libcore/num/uint-template.rs b/src/libcore/num/uint-template.rs index 0f74b73e1c5..adfd50e20e7 100644 --- a/src/libcore/num/uint-template.rs +++ b/src/libcore/num/uint-template.rs @@ -130,21 +130,6 @@ impl T : Eq { pure fn ne(&self, other: &T) -> bool { return (*self) != (*other); } } -impl T: num::Num { - #[inline(always)] - pure fn add(&self, other: &T) -> T { return *self + *other; } - #[inline(always)] - pure fn sub(&self, other: &T) -> T { return *self - *other; } - #[inline(always)] - pure fn mul(&self, other: &T) -> T { return *self * *other; } - #[inline(always)] - pure fn div(&self, other: &T) -> T { return *self / *other; } - #[inline(always)] - pure fn modulo(&self, other: &T) -> T { return *self % *other; } - #[inline(always)] - pure fn neg(&self) -> T { return -*self; } -} - impl T: num::Zero { #[inline(always)] static pure fn zero() -> T { 0 } @@ -167,6 +152,31 @@ impl T: num::Round { pure fn fract(&self) -> T { 0 } } +#[cfg(notest)] +impl ops::Add for T { + pure fn add(&self, other: &T) -> T { *self + *other } +} +#[cfg(notest)] +impl ops::Sub for T { + pure fn sub(&self, other: &T) -> T { *self - *other } +} +#[cfg(notest)] +impl ops::Mul for T { + pure fn mul(&self, other: &T) -> T { *self * *other } +} +#[cfg(notest)] +impl ops::Div for T { + pure fn div(&self, other: &T) -> T { *self / *other } +} +#[cfg(notest)] +impl ops::Modulo for T { + pure fn modulo(&self, other: &T) -> T { *self % *other } +} +#[cfg(notest)] +impl ops::Neg for T { + pure fn neg(&self) -> T { -*self } +} + // String conversion functions and impl str -> num /// Parse a string as a number in base 10. diff --git a/src/libcore/prelude.rs b/src/libcore/prelude.rs index 5b4726d482d..b50fa265f03 100644 --- a/src/libcore/prelude.rs +++ b/src/libcore/prelude.rs @@ -29,7 +29,7 @@ pub use container::{Container, Mutable, Map, Set}; pub use hash::Hash; pub use iter::{BaseIter, ExtendedIter, EqIter, CopyableIter}; pub use iter::{CopyableOrderedIter, CopyableNonstrictIter, Times}; -pub use num::{Num, NumCast}; +pub use num::NumCast; pub use path::GenericPath; pub use path::Path; pub use path::PosixPath; diff --git a/src/test/compile-fail/autoderef-full-lval.rs b/src/test/compile-fail/autoderef-full-lval.rs index c76bd192e6a..fec5c994de7 100644 --- a/src/test/compile-fail/autoderef-full-lval.rs +++ b/src/test/compile-fail/autoderef-full-lval.rs @@ -8,7 +8,7 @@ // option. This file may not be copied, modified, or distributed // except according to those terms. -// error-pattern: binary operation + cannot be applied to type +// error-pattern: mismatched types type clam = {x: @int, y: @int}; type fish = {a: @int}; diff --git a/src/test/run-pass/issue-3149.rs b/src/test/run-pass/issue-3149.rs index 805aac92937..df102f93c2b 100644 --- a/src/test/run-pass/issue-3149.rs +++ b/src/test/run-pass/issue-3149.rs @@ -8,11 +8,11 @@ // option. This file may not be copied, modified, or distributed // except according to those terms. -pure fn Matrix4(m11: T, m12: T, m13: T, m14: T, - m21: T, m22: T, m23: T, m24: T, - m31: T, m32: T, m33: T, m34: T, - m41: T, m42: T, m43: T, m44: T) - -> Matrix4 { +pure fn Matrix4(m11: T, m12: T, m13: T, m14: T, + m21: T, m22: T, m23: T, m24: T, + m31: T, m32: T, m33: T, m34: T, + m41: T, m42: T, m43: T, m44: T) + -> Matrix4 { Matrix4 { m11: m11, m12: m12, m13: m13, m14: m14, diff --git a/src/test/run-pass/trait-inheritance-num.rs b/src/test/run-pass/trait-inheritance-num.rs index c7a049b2f34..4e46d6b2b18 100644 --- a/src/test/run-pass/trait-inheritance-num.rs +++ b/src/test/run-pass/trait-inheritance-num.rs @@ -16,7 +16,7 @@ use num::NumCast::from; extern mod std; use std::cmp::FuzzyEq; -pub trait NumExt: Num NumCast Eq Ord {} +pub trait NumExt: NumCast Eq Ord {} pub trait FloatExt: NumExt FuzzyEq {} diff --git a/src/test/run-pass/trait-inheritance-num1.rs b/src/test/run-pass/trait-inheritance-num1.rs index a9cbd4e622c..03230dc39af 100644 --- a/src/test/run-pass/trait-inheritance-num1.rs +++ b/src/test/run-pass/trait-inheritance-num1.rs @@ -8,12 +8,10 @@ // option. This file may not be copied, modified, or distributed // except according to those terms. -// Using the real Num from core - use cmp::Ord; use num::NumCast::from; -pub trait NumExt: Num NumCast Ord { } +pub trait NumExt: NumCast Ord { } fn greater_than_one(n: &T) -> bool { *n > from(1) diff --git a/src/test/run-pass/trait-inheritance-num2.rs b/src/test/run-pass/trait-inheritance-num2.rs index 6829990bc5a..fb2969a8398 100644 --- a/src/test/run-pass/trait-inheritance-num2.rs +++ b/src/test/run-pass/trait-inheritance-num2.rs @@ -38,7 +38,7 @@ pub impl f64: TypeExt {} pub impl float: TypeExt {} -pub trait NumExt: TypeExt Eq Ord Num NumCast {} +pub trait NumExt: TypeExt Eq Ord NumCast {} pub impl u8: NumExt {} pub impl u16: NumExt {} diff --git a/src/test/run-pass/trait-inheritance-num3.rs b/src/test/run-pass/trait-inheritance-num3.rs index 32775164d35..30cc5423022 100644 --- a/src/test/run-pass/trait-inheritance-num3.rs +++ b/src/test/run-pass/trait-inheritance-num3.rs @@ -11,7 +11,7 @@ use cmp::{Eq, Ord}; use num::NumCast::from; -pub trait NumExt: Eq Ord Num NumCast {} +pub trait NumExt: Eq Ord NumCast {} pub impl f32: NumExt {} @@ -19,4 +19,4 @@ fn num_eq_one(n: T) { io::println(fmt!("%?", n == from(1))) } pub fn main() { num_eq_one(1f32); // you need to actually use the function to trigger the ICE -} \ No newline at end of file +} diff --git a/src/test/run-pass/trait-inheritance-num5.rs b/src/test/run-pass/trait-inheritance-num5.rs index 13c75224e5f..c2b88c59f87 100644 --- a/src/test/run-pass/trait-inheritance-num5.rs +++ b/src/test/run-pass/trait-inheritance-num5.rs @@ -11,7 +11,7 @@ use cmp::{Eq, Ord}; use num::NumCast::from; -pub trait NumExt: Eq Num NumCast {} +pub trait NumExt: Eq NumCast {} pub impl f32: NumExt {} pub impl int: NumExt {}