今天就来学习记录下Rust
中的必掌握知识之 Trait
。
Trait
是Rust
中的接口,可以为不同的类型提供同一类行为(函数)。
定义一个 Trait
1 2 3 4 5 6 7 8
| pub trait Summary { fn summarize_author(&self) -> String;
fn summarize(&self) -> String { format!("(Read more from {})", self.summarize_author()) } }
|
上面代码定义了一个名字为 Summary
的 Trait
,并且里面分别声明了一个名为 summarize_author() 的函数和一个函数定义 summarize()
。
定义两个结构体并且实现 Summary Trait
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28
| pub struct NewsArticle { pub headline: String, pub location: String, pub author: String, pub content: String, }
impl Summary for NewsArticle { fn summarize_author(&self) -> String { format!("@{}", self.headline) } }
pub struct Tweet { pub username: String, pub content: String, pub reply: bool, pub retweet: bool, }
impl Summary for Tweet { fn summarize_author(&self) -> String { format!("@{}", self.username) } }
|
把 Trait
作为参数
把 Trait
用作函数参数可以实现让该函数接受不同的类型实参,只要该类型实现了 该 Trait 就行。
1 2 3
| pub fn notify(item: &impl Summary) { println!("Breaking news! {}", item.summarize()); }
|
Trait Bound
语法
1 2 3
| pub fn notify<T: Summary>(item: &T) { println!("Breaking news! {}", item.summarize()); }
|
多个参数例子:
1 2 3 4
| pub fn notify<T: Summary>(item: &T, item2: &T) { println!("Breaking news! {}", item.summarize()); println!("Breaking news! {}", item2.summarize()); }
|
多种类型例子:
1 2 3 4
| pub fn notify<T: Summary, U: Summary>(item: &T, item2: &U) { println!("Breaking news! {}", item.summarize()); println!("Breaking news! {}", item2.summarize()); }
|
Where 语法
1 2 3 4 5 6
| pub fn print_summary<T>(item: &T) where T: super::Summary, { println!("print_summary: {}", item.summarize()); }
|
让参数实现多个 Trait
1 2 3 4 5 6
| pub fn notify1<T>(item: &T) where T: super::Summary + Display, { println!("notify1: {}", item); }
|
方式2
1 2 3
| pub fn notify<T: Summary + Display>(item: &T) { println!("Breaking news! {}", item.summarize()); }
|
返回 Trait
类型
求最大数
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15
|
fn largest<T>(list: &[T]) -> T where T: PartialOrd + Copy, { let mut largest = list[0];
for &item in list { if item > largest { largest = item; } } largest }
|