use assoc types in binop traits
This commit is contained in:
parent
7095dd0070
commit
99017f82b6
36 changed files with 375 additions and 156 deletions
|
|
@ -8,10 +8,12 @@
|
|||
// option. This file may not be copied, modified, or distributed
|
||||
// except according to those terms.
|
||||
|
||||
#![feature(associated_types)]
|
||||
|
||||
use std::cmp::PartialEq;
|
||||
use std::ops::{Add, Sub, Mul};
|
||||
|
||||
pub trait MyNum : Add<Self,Self> + Sub<Self,Self> + Mul<Self,Self> + PartialEq + Clone {
|
||||
pub trait MyNum : Add<Output=Self> + Sub<Output=Self> + Mul<Output=Self> + PartialEq + Clone {
|
||||
}
|
||||
|
||||
#[derive(Clone, Show)]
|
||||
|
|
@ -19,15 +21,21 @@ pub struct MyInt {
|
|||
pub val: int
|
||||
}
|
||||
|
||||
impl Add<MyInt, MyInt> for MyInt {
|
||||
impl Add for MyInt {
|
||||
type Output = MyInt;
|
||||
|
||||
fn add(self, other: MyInt) -> MyInt { mi(self.val + other.val) }
|
||||
}
|
||||
|
||||
impl Sub<MyInt, MyInt> for MyInt {
|
||||
impl Sub for MyInt {
|
||||
type Output = MyInt;
|
||||
|
||||
fn sub(self, other: MyInt) -> MyInt { mi(self.val - other.val) }
|
||||
}
|
||||
|
||||
impl Mul<MyInt, MyInt> for MyInt {
|
||||
impl Mul for MyInt {
|
||||
type Output = MyInt;
|
||||
|
||||
fn mul(self, other: MyInt) -> MyInt { mi(self.val * other.val) }
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -21,7 +21,7 @@ pub fn has_closures() -> uint {
|
|||
f() + g()
|
||||
}
|
||||
|
||||
pub fn has_generic_closures<T: Add<T,T> + Copy>(x: T, y: T) -> T {
|
||||
pub fn has_generic_closures<T: Add<Output=T> + Copy>(x: T, y: T) -> T {
|
||||
let mut f = move |&mut:| x;
|
||||
let g = |:| y;
|
||||
f() + g()
|
||||
|
|
|
|||
|
|
@ -10,63 +10,65 @@
|
|||
|
||||
// Test that binary operators consume their arguments
|
||||
|
||||
#![feature(associated_types, default_type_params)]
|
||||
|
||||
use std::ops::{Add, Sub, Mul, Div, Rem, BitAnd, BitXor, BitOr, Shl, Shr};
|
||||
|
||||
fn add<A: Add<B, ()>, B>(lhs: A, rhs: B) {
|
||||
fn add<A: Add<B, Output=()>, B>(lhs: A, rhs: B) {
|
||||
lhs + rhs;
|
||||
drop(lhs); //~ ERROR use of moved value: `lhs`
|
||||
drop(rhs); //~ ERROR use of moved value: `rhs`
|
||||
}
|
||||
|
||||
fn sub<A: Sub<B, ()>, B>(lhs: A, rhs: B) {
|
||||
fn sub<A: Sub<B, Output=()>, B>(lhs: A, rhs: B) {
|
||||
lhs - rhs;
|
||||
drop(lhs); //~ ERROR use of moved value: `lhs`
|
||||
drop(rhs); //~ ERROR use of moved value: `rhs`
|
||||
}
|
||||
|
||||
fn mul<A: Mul<B, ()>, B>(lhs: A, rhs: B) {
|
||||
fn mul<A: Mul<B, Output=()>, B>(lhs: A, rhs: B) {
|
||||
lhs * rhs;
|
||||
drop(lhs); //~ ERROR use of moved value: `lhs`
|
||||
drop(rhs); //~ ERROR use of moved value: `rhs`
|
||||
}
|
||||
|
||||
fn div<A: Div<B, ()>, B>(lhs: A, rhs: B) {
|
||||
fn div<A: Div<B, Output=()>, B>(lhs: A, rhs: B) {
|
||||
lhs / rhs;
|
||||
drop(lhs); //~ ERROR use of moved value: `lhs`
|
||||
drop(rhs); //~ ERROR use of moved value: `rhs`
|
||||
}
|
||||
|
||||
fn rem<A: Rem<B, ()>, B>(lhs: A, rhs: B) {
|
||||
fn rem<A: Rem<B, Output=()>, B>(lhs: A, rhs: B) {
|
||||
lhs % rhs;
|
||||
drop(lhs); //~ ERROR use of moved value: `lhs`
|
||||
drop(rhs); //~ ERROR use of moved value: `rhs`
|
||||
}
|
||||
|
||||
fn bitand<A: BitAnd<B, ()>, B>(lhs: A, rhs: B) {
|
||||
fn bitand<A: BitAnd<B, Output=()>, B>(lhs: A, rhs: B) {
|
||||
lhs & rhs;
|
||||
drop(lhs); //~ ERROR use of moved value: `lhs`
|
||||
drop(rhs); //~ ERROR use of moved value: `rhs`
|
||||
}
|
||||
|
||||
fn bitor<A: BitOr<B, ()>, B>(lhs: A, rhs: B) {
|
||||
fn bitor<A: BitOr<B, Output=()>, B>(lhs: A, rhs: B) {
|
||||
lhs | rhs;
|
||||
drop(lhs); //~ ERROR use of moved value: `lhs`
|
||||
drop(rhs); //~ ERROR use of moved value: `rhs`
|
||||
}
|
||||
|
||||
fn bitxor<A: BitXor<B, ()>, B>(lhs: A, rhs: B) {
|
||||
fn bitxor<A: BitXor<B, Output=()>, B>(lhs: A, rhs: B) {
|
||||
lhs ^ rhs;
|
||||
drop(lhs); //~ ERROR use of moved value: `lhs`
|
||||
drop(rhs); //~ ERROR use of moved value: `rhs`
|
||||
}
|
||||
|
||||
fn shl<A: Shl<B, ()>, B>(lhs: A, rhs: B) {
|
||||
fn shl<A: Shl<B, Output=()>, B>(lhs: A, rhs: B) {
|
||||
lhs << rhs;
|
||||
drop(lhs); //~ ERROR use of moved value: `lhs`
|
||||
drop(rhs); //~ ERROR use of moved value: `rhs`
|
||||
}
|
||||
|
||||
fn shr<A: Shr<B, ()>, B>(lhs: A, rhs: B) {
|
||||
fn shr<A: Shr<B, Output=()>, B>(lhs: A, rhs: B) {
|
||||
lhs >> rhs;
|
||||
drop(lhs); //~ ERROR use of moved value: `lhs`
|
||||
drop(rhs); //~ ERROR use of moved value: `rhs`
|
||||
|
|
|
|||
|
|
@ -10,21 +10,23 @@
|
|||
|
||||
// Test that move restrictions are enforced on overloaded binary operations
|
||||
|
||||
#![feature(associated_types, default_type_params)]
|
||||
|
||||
use std::ops::Add;
|
||||
|
||||
fn double_move<T: Add<T, ()>>(x: T) {
|
||||
fn double_move<T: Add<Output=()>>(x: T) {
|
||||
x
|
||||
+
|
||||
x; //~ ERROR: use of moved value
|
||||
}
|
||||
|
||||
fn move_then_borrow<T: Add<T, ()> + Clone>(x: T) {
|
||||
fn move_then_borrow<T: Add<Output=()> + Clone>(x: T) {
|
||||
x
|
||||
+
|
||||
x.clone(); //~ ERROR: use of moved value
|
||||
}
|
||||
|
||||
fn move_borrowed<T: Add<T, ()>>(x: T, mut y: T) {
|
||||
fn move_borrowed<T: Add<Output=()>>(x: T, mut y: T) {
|
||||
let m = &x;
|
||||
let n = &mut y;
|
||||
|
||||
|
|
@ -33,7 +35,7 @@ fn move_borrowed<T: Add<T, ()>>(x: T, mut y: T) {
|
|||
y; //~ ERROR: cannot move out of `y` because it is borrowed
|
||||
}
|
||||
|
||||
fn illegal_dereference<T: Add<T, ()>>(mut x: T, y: T) {
|
||||
fn illegal_dereference<T: Add<Output=()>>(mut x: T, y: T) {
|
||||
let m = &mut x;
|
||||
let n = &y;
|
||||
|
||||
|
|
@ -44,11 +46,15 @@ fn illegal_dereference<T: Add<T, ()>>(mut x: T, y: T) {
|
|||
|
||||
struct Foo;
|
||||
|
||||
impl<'a, 'b> Add<&'b Foo, ()> for &'a mut Foo {
|
||||
impl<'a, 'b> Add<&'b Foo> for &'a mut Foo {
|
||||
type Output = ();
|
||||
|
||||
fn add(self, _: &Foo) {}
|
||||
}
|
||||
|
||||
impl<'a, 'b> Add<&'b mut Foo, ()> for &'a Foo {
|
||||
impl<'a, 'b> Add<&'b mut Foo> for &'a Foo {
|
||||
type Output = ();
|
||||
|
||||
fn add(self, _: &mut Foo) {}
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -8,12 +8,16 @@
|
|||
// option. This file may not be copied, modified, or distributed
|
||||
// except according to those terms.
|
||||
|
||||
#![feature(associated_types)]
|
||||
|
||||
use std::ops::Add;
|
||||
|
||||
#[derive(Clone)]
|
||||
struct foo(Box<uint>);
|
||||
|
||||
impl Add<foo, foo> for foo {
|
||||
impl Add for foo {
|
||||
type Output = foo;
|
||||
|
||||
fn add(self, f: foo) -> foo {
|
||||
let foo(box i) = self;
|
||||
let foo(box j) = f;
|
||||
|
|
|
|||
|
|
@ -8,6 +8,8 @@
|
|||
// option. This file may not be copied, modified, or distributed
|
||||
// except according to those terms.
|
||||
|
||||
#![feature(associated_types, default_type_params)]
|
||||
|
||||
use std::ops::Add;
|
||||
|
||||
#[derive(Copy)]
|
||||
|
|
@ -16,7 +18,9 @@ struct Point {
|
|||
y: int,
|
||||
}
|
||||
|
||||
impl Add<int, int> for Point {
|
||||
impl Add<int> for Point {
|
||||
type Output = int;
|
||||
|
||||
fn add(self, z: int) -> int {
|
||||
self.x + self.y + z
|
||||
}
|
||||
|
|
|
|||
|
|
@ -8,7 +8,6 @@
|
|||
// option. This file may not be copied, modified, or distributed
|
||||
// except according to those terms.
|
||||
|
||||
|
||||
trait vec_monad<A> {
|
||||
fn bind<B>(&self, f: |A| -> Vec<B> );
|
||||
}
|
||||
|
|
|
|||
|
|
@ -13,6 +13,8 @@
|
|||
// (In this case the mul method should take &f64 and not f64)
|
||||
// See: #11450
|
||||
|
||||
#![feature(associated_types, default_type_params)]
|
||||
|
||||
use std::ops::Mul;
|
||||
|
||||
struct Vec1 {
|
||||
|
|
@ -20,7 +22,9 @@ struct Vec1 {
|
|||
}
|
||||
|
||||
// Expecting value in input signature
|
||||
impl Mul<f64, Vec1> for Vec1 {
|
||||
impl Mul<f64> for Vec1 {
|
||||
type Output = Vec1;
|
||||
|
||||
fn mul(self, s: &f64) -> Vec1 {
|
||||
//~^ ERROR: method `mul` has an incompatible type for trait: expected f64, found &-ptr
|
||||
Vec1 {
|
||||
|
|
@ -35,7 +39,9 @@ struct Vec2 {
|
|||
}
|
||||
|
||||
// Wrong type parameter ordering
|
||||
impl Mul<Vec2, f64> for Vec2 {
|
||||
impl Mul<Vec2> for Vec2 {
|
||||
type Output = f64;
|
||||
|
||||
fn mul(self, s: f64) -> Vec2 {
|
||||
//~^ ERROR: method `mul` has an incompatible type for trait: expected struct Vec2, found f64
|
||||
Vec2 {
|
||||
|
|
@ -52,7 +58,9 @@ struct Vec3 {
|
|||
}
|
||||
|
||||
// Unexpected return type
|
||||
impl Mul<f64, i32> for Vec3 {
|
||||
impl Mul<f64> for Vec3 {
|
||||
type Output = i32;
|
||||
|
||||
fn mul(self, s: f64) -> f64 {
|
||||
//~^ ERROR: method `mul` has an incompatible type for trait: expected i32, found f64
|
||||
s
|
||||
|
|
|
|||
|
|
@ -8,13 +8,17 @@
|
|||
// option. This file may not be copied, modified, or distributed
|
||||
// except according to those terms.
|
||||
|
||||
use std::ops::Add;
|
||||
#![feature(associated_types)]
|
||||
|
||||
use std::num::Zero;
|
||||
use std::ops::Add;
|
||||
|
||||
#[derive(Zero)]
|
||||
struct Vector2<T>(T, T);
|
||||
|
||||
impl<T: Add<T, T>> Add<Vector2<T>, Vector2<T>> for Vector2<T> {
|
||||
impl<T: Add<Output=T>> Add for Vector2<T> {
|
||||
type Output = Vector2<T>;
|
||||
|
||||
fn add(self, other: Vector2<T>) -> Vector2<T> {
|
||||
match (self, other) {
|
||||
(Vector2(x0, y0), Vector2(x1, y1)) => {
|
||||
|
|
@ -29,7 +33,9 @@ struct Vector3<T> {
|
|||
x: T, y: T, z: T,
|
||||
}
|
||||
|
||||
impl<T: Add<T, T>> Add<Vector3<T>, Vector3<T>> for Vector3<T> {
|
||||
impl<T: Add<Output=T>> Add for Vector3<T> {
|
||||
type Output = Vector3<T>;
|
||||
|
||||
fn add(self, other: Vector3<T>) -> Vector3<T> {
|
||||
Vector3 {
|
||||
x: self.x + other.x,
|
||||
|
|
@ -46,7 +52,9 @@ struct Matrix3x2<T> {
|
|||
z: Vector2<T>,
|
||||
}
|
||||
|
||||
impl<T: Add<T, T>> Add<Matrix3x2<T>, Matrix3x2<T>> for Matrix3x2<T> {
|
||||
impl<T: Add<Output=T>> Add for Matrix3x2<T> {
|
||||
type Output = Matrix3x2<T>;
|
||||
|
||||
fn add(self, other: Matrix3x2<T>) -> Matrix3x2<T> {
|
||||
Matrix3x2 {
|
||||
x: self.x + other.x,
|
||||
|
|
|
|||
|
|
@ -10,7 +10,7 @@
|
|||
|
||||
// If `Mul` used an associated type for its output, this test would
|
||||
// work more smoothly.
|
||||
#![feature(old_orphan_check)]
|
||||
#![feature(associated_types, default_type_params, old_orphan_check)]
|
||||
|
||||
use std::ops::Mul;
|
||||
|
||||
|
|
@ -33,7 +33,9 @@ impl Vec2 {
|
|||
trait RhsOfVec2Mul<Result> { fn mul_vec2_by(&self, lhs: &Vec2) -> Result; }
|
||||
|
||||
// Vec2's implementation of Mul "from the other side" using the above trait
|
||||
impl<Res, Rhs: RhsOfVec2Mul<Res>> Mul<Rhs,Res> for Vec2 {
|
||||
impl<Res, Rhs: RhsOfVec2Mul<Res>> Mul<Rhs> for Vec2 {
|
||||
type Output = Res;
|
||||
|
||||
fn mul(self, rhs: Rhs) -> Res { rhs.mul_vec2_by(&self) }
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -15,7 +15,7 @@ trait Positioned<S> {
|
|||
fn X(&self) -> S;
|
||||
}
|
||||
|
||||
trait Movable<S: Add<S, S>>: Positioned<S> {
|
||||
trait Movable<S: Add<Output=S>>: Positioned<S> {
|
||||
fn translate(&mut self, dx: S) {
|
||||
let x = self.X() + dx;
|
||||
self.SetX(x);
|
||||
|
|
|
|||
|
|
@ -12,7 +12,7 @@
|
|||
|
||||
use std::ops::Add;
|
||||
|
||||
fn foo<T: Add<T, T> + Clone>([x, y, z]: [T; 3]) -> (T, T, T) {
|
||||
fn foo<T: Add<Output=T> + Clone>([x, y, z]: [T; 3]) -> (T, T, T) {
|
||||
(x.clone(), x.clone() + y.clone(), x + y + z)
|
||||
}
|
||||
fn bar(a: &'static str, b: &'static str) -> [&'static str; 4] {
|
||||
|
|
|
|||
|
|
@ -11,6 +11,8 @@
|
|||
// Test that we can overload the `+` operator for points so that two
|
||||
// points can be added, and a point can be added to an integer.
|
||||
|
||||
#![feature(associated_types, default_type_params)]
|
||||
|
||||
use std::ops;
|
||||
|
||||
#[derive(Show,PartialEq,Eq)]
|
||||
|
|
@ -19,13 +21,17 @@ struct Point {
|
|||
y: int
|
||||
}
|
||||
|
||||
impl ops::Add<Point,Point> for Point {
|
||||
impl ops::Add for Point {
|
||||
type Output = Point;
|
||||
|
||||
fn add(self, other: Point) -> Point {
|
||||
Point {x: self.x + other.x, y: self.y + other.y}
|
||||
}
|
||||
}
|
||||
|
||||
impl ops::Add<int,Point> for Point {
|
||||
impl ops::Add<int> for Point {
|
||||
type Output = Point;
|
||||
|
||||
fn add(self, other: int) -> Point {
|
||||
Point {x: self.x + other,
|
||||
y: self.y + other}
|
||||
|
|
|
|||
|
|
@ -8,6 +8,7 @@
|
|||
// option. This file may not be copied, modified, or distributed
|
||||
// except according to those terms.
|
||||
|
||||
#![feature(associated_types)]
|
||||
|
||||
use std::cmp;
|
||||
use std::ops;
|
||||
|
|
@ -18,13 +19,17 @@ struct Point {
|
|||
y: int
|
||||
}
|
||||
|
||||
impl ops::Add<Point,Point> for Point {
|
||||
impl ops::Add for Point {
|
||||
type Output = Point;
|
||||
|
||||
fn add(self, other: Point) -> Point {
|
||||
Point {x: self.x + other.x, y: self.y + other.y}
|
||||
}
|
||||
}
|
||||
|
||||
impl ops::Sub<Point,Point> for Point {
|
||||
impl ops::Sub for Point {
|
||||
type Output = Point;
|
||||
|
||||
fn sub(self, other: Point) -> Point {
|
||||
Point {x: self.x - other.x, y: self.y - other.y}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -10,14 +10,14 @@
|
|||
|
||||
// Tests that nested vtables work with overloaded calls.
|
||||
|
||||
#![feature(unboxed_closures)]
|
||||
#![feature(default_type_params, unboxed_closures)]
|
||||
|
||||
use std::ops::Fn;
|
||||
use std::ops::Add;
|
||||
|
||||
struct G<A>;
|
||||
|
||||
impl<'a, A: Add<int, int>> Fn<(A,), int> for G<A> {
|
||||
impl<'a, A: Add<int, Output=int>> Fn<(A,), int> for G<A> {
|
||||
extern "rust-call" fn call(&self, (arg,): (A,)) -> int {
|
||||
arg.add(1)
|
||||
}
|
||||
|
|
|
|||
|
|
@ -9,7 +9,7 @@
|
|||
// except according to those terms.
|
||||
|
||||
|
||||
#![feature(simd)]
|
||||
#![feature(associated_types, simd)]
|
||||
|
||||
use std::ops;
|
||||
|
||||
|
|
@ -17,11 +17,13 @@ use std::ops;
|
|||
|
||||
impl Copy for f32x4 {}
|
||||
|
||||
fn add<T: ops::Add<T, T>>(lhs: T, rhs: T) -> T {
|
||||
fn add<T: ops::Add<Output=T>>(lhs: T, rhs: T) -> T {
|
||||
lhs + rhs
|
||||
}
|
||||
|
||||
impl ops::Add<f32x4, f32x4> for f32x4 {
|
||||
impl ops::Add for f32x4 {
|
||||
type Output = f32x4;
|
||||
|
||||
fn add(self, rhs: f32x4) -> f32x4 {
|
||||
self + rhs
|
||||
}
|
||||
|
|
|
|||
|
|
@ -17,7 +17,7 @@ trait Positioned<S> {
|
|||
fn X(&self) -> S;
|
||||
}
|
||||
|
||||
trait Movable<S: Add<S, S>>: Positioned<S> {
|
||||
trait Movable<S: Add<Output=S>>: Positioned<S> {
|
||||
fn translate(&mut self, dx: S) {
|
||||
let x = self.X() + dx;
|
||||
self.SetX(x);
|
||||
|
|
@ -35,7 +35,7 @@ impl<S: Clone> Positioned<S> for Point<S> {
|
|||
}
|
||||
}
|
||||
|
||||
impl<S: Clone + Add<S, S>> Movable<S> for Point<S> {}
|
||||
impl<S: Clone + Add<Output=S>> Movable<S> for Point<S> {}
|
||||
|
||||
pub fn main() {
|
||||
let mut p = Point{ x: 1i, y: 2i};
|
||||
|
|
|
|||
|
|
@ -8,23 +8,31 @@
|
|||
// option. This file may not be copied, modified, or distributed
|
||||
// except according to those terms.
|
||||
|
||||
#![feature(associated_types)]
|
||||
|
||||
use std::cmp::PartialEq;
|
||||
use std::ops::{Add, Sub, Mul};
|
||||
|
||||
trait MyNum : Add<Self,Self> + Sub<Self,Self> + Mul<Self,Self> + PartialEq + Clone { }
|
||||
trait MyNum : Add<Output=Self> + Sub<Output=Self> + Mul<Output=Self> + PartialEq + Clone { }
|
||||
|
||||
#[derive(Clone, Show)]
|
||||
struct MyInt { val: int }
|
||||
|
||||
impl Add<MyInt, MyInt> for MyInt {
|
||||
impl Add for MyInt {
|
||||
type Output = MyInt;
|
||||
|
||||
fn add(self, other: MyInt) -> MyInt { mi(self.val + other.val) }
|
||||
}
|
||||
|
||||
impl Sub<MyInt, MyInt> for MyInt {
|
||||
impl Sub for MyInt {
|
||||
type Output = MyInt;
|
||||
|
||||
fn sub(self, other: MyInt) -> MyInt { mi(self.val - other.val) }
|
||||
}
|
||||
|
||||
impl Mul<MyInt, MyInt> for MyInt {
|
||||
impl Mul for MyInt {
|
||||
type Output = MyInt;
|
||||
|
||||
fn mul(self, other: MyInt) -> MyInt { mi(self.val * other.val) }
|
||||
}
|
||||
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue