对象到特征的转换

Object to trait conversion

假设以下 Rust 代码:

trait  MyTrait {...}
struct MyStruct;
impl   MyTrait for MyStruct {...}
impl   MyStruct {
     pub fn new() -> MyStruct { MyStruct{...} }
}

我会写:

let foo: MyStruct = MyStruct::new();

但是我不能

let bar: MyTrait  = MyStruct::new();

其他面向接口的编程语言可以做到这一点。我错过了什么吗?如何将各种对象传递给只接受 MyTrait 的方法?我需要使用 "templates" 例如 my_method<T: MyTrait>(param: T) {...} 吗?

您不需要将 bar 定义为 MyTrait 对象。 (这甚至是错误的想法,因为 Rust 并没有真正的继承。将特征更像是 Java 中的接口。在这种情况下,您似乎将 MyTrait 视为超类MyStruct)

你可以做到

let bar = MyStruct::new();

然后将它传递给这样定义的函数:

fn my_method<T: MyTrait>(param: T) {...}

my_method(bar)

这是有效的,因为 Rust 静态检查类型 MyStructbar 实现了特征 MyTrait.

旁注:如果要创建特征对象向量,请查看 this 问题。

这是因为一个特性可能被多种类型实现,因此 bar 的大小是未知的。但是参考的大小是已知的,所以下面的工作。

trait MyTrait {}
struct MyStruct;
impl MyTrait for MyStruct {}
impl MyStruct {
    fn new() -> Self {
        MyStruct
    }
}

fn main() {
    let foo: MyStruct = MyStruct::new();
    let bar: &MyTrait = &MyStruct::new();
}

请注意 bar 不是 MyTrait,而是 &MyTrait,这称为 trait object