trait Counter {
fn count(&self) -> i32;
}
struct AddCounter {
a: i32,
b: i32,
}
impl Counter for AddCounter {
fn count(&self) -> i32 {
self.a + self.b
}
}
struct MulCounter {
a: i32,
b: i32,
}
impl Counter for MulCounter {
fn count(&self) -> i32 {
self.a * self.b
}
}
fn get_counter(a: i32, b: i32, op: &str) -> impl Counter {
match op {
"+" => AddCounter { a, b },
"*" => MulCounter { a, b },
_ => panic!(format!("{}{}", "??????", op)),
}
}
fn main() {}
Run Code Online (Sandbox Code Playgroud)
我打电话时收到错误get_counter(...):
error[E0308]: match arms have incompatible types
--> src/main.rs:26:5
|
26 | / match op {
27 | | "+" => AddCounter { a, b },
28 | | "*" => MulCounter { a, b },
| | ------------------- match arm with an incompatible type
29 | | _ => panic!(format!("{}{}", "??????", op)),
30 | | }
| |_____^ expected struct `AddCounter`, found struct `MulCounter`
|
= note: expected type `AddCounter`
found type `MulCounter`
Run Code Online (Sandbox Code Playgroud)
将impl Trait表示法视为通用类型.你不能写:
fn get_counter<T>(a: i32, b: i32, op: &str) -> T {
match op {
"+" => AddCounter { a, b },
"*" => MulCounter { a, b },
_ => panic!(format!("{}{}", "??????", op)),
}
}
Run Code Online (Sandbox Code Playgroud)
因为AddCounter并且MulCounter没有相同的类型:是什么T?
您可以使用动态分派而不是静态分派:
fn get_counter(a: i32, b: i32, op: &str) -> Box<dyn Counter> {
match op {
"+" => Box::new(AddCounter { a, b }),
"*" => Box::new(MulCounter { a, b }),
_ => panic!(format!("{}{}", "??????", op)),
}
}
Run Code Online (Sandbox Code Playgroud)
当您使用静态分派时,Rust编译器将代码单一化:它为泛型类型的每个值生成一个新函数(有关详细信息,请参阅什么是与C++的上下文的单态化?).每个返回值都是"真实"普通类型.在这种情况下,函数不能返回(例如)String一个路径和i32另一个路径.
在动态分派的情况下,它不是返回的"真实"类型而是特征对象:编译器不知道真实类型; 它只关心特征对象可以用作特征实现者.这就是你需要的.
| 归档时间: |
|
| 查看次数: |
561 次 |
| 最近记录: |