rust 中,范型可以使用 trait 类型来约束,限定必须是实现了此 trait 的类型才符合要求,且 trait 可以有关联类型,以 std::ops::Add 为例,在标准库中 Add 的定义如下:
pub trait Add<Rhs = Self> {
type Output;
fn add(self, rhs: Rhs) -> Self::Output;
}
复制代码
Output 为关联类型,在使用 trait 限定且实际类型要应用该 trait 时,要明确指明 Output 的类型。
例如:有一个 struct Point,有两个属性 x 和 y,且都定义为 T 类型,T 类型使用 trait 限定为 Add 类型,定义如下:
use std::ops::Add;
#[derive(Debug, PartialEq)]
struct Point<T: Add> {
x: T,
y: T,
}
复制代码
此时,想让 Point 本身也实现 Add trait,且 where 后面的 T 类型,明确说明了是 Add 类型,且指明了 Add 的关联类型 Output 的类型也是 T,这时 Point 才能正常参加加法运算,代码如下:
impl<T> Add for Point<T> where T: Add<Output=T>{
type Output = Point<T>;
fn add(self, rhs: Self) -> Self::Output {
Point{
x: self.x + rhs.x,
y: self.y + rhs.y,
}
}
}
复制代码
此时,Point 已经实现了 Add trait,可以实现加法(+)操作,且结果为 true,代码如下:
fn main() {
let p1 = Point{x: 1, y: 1};
let p2 = Point{x: 2, y: 2};
assert_eq!(Point{x: 3, y: 3}, p1 + p2);
}
复制代码
如果在为 Point 实现 Add trait 时,不指明 Add 的关联类型 Output,则会报错,代码如下:
impl<T> Add for Point<T> where T: Add{
type Output = Point<T>;
fn add(self, rhs: Self) -> Self::Output {
Point{
x: self.x + rhs.x,
y: self.y + rhs.y,
}
}
}
复制代码
报错信息如下:
mismatched types
expected type parameter `T`
found associated type `<T as Add>::Output`
复制代码
评论