如何从 Box<dyn T> 获取 &dyn T

qin*_*oon 4 rust

&dyn T我正在尝试从 a获取a Box<dyn T>,如以下示例所示。但是,它无法编译。

trait MyTrait {
    
}

struct Foo;
impl MyTrait for Foo {}

fn main() {
    let b: Box<dyn MyTrait> = Box::new(Foo);
    let c: &dyn MyTrait = &b;
}
Run Code Online (Sandbox Code Playgroud)

https://play.rust-lang.org/?version=stable&mode=debug&edition=2018&gist=69c72904fbceae5b55470a878a441b7d

错误信息是

error[E0277]: the trait bound `Box<dyn MyTrait>: MyTrait` is not satisfied
  --> src/main.rs:10:27
   |
10 |     let c: &dyn MyTrait = &b;
   |                           ^^ the trait `MyTrait` is not implemented for `Box<dyn MyTrait>`
   |
   = note: required for the cast to the object type `dyn MyTrait`
Run Code Online (Sandbox Code Playgroud)

很明显,你可以&T从 a得到 a Box<T>。我不明白为什么你不能&dyn T从 a获得 a Box<dyn T>

kmd*_*eko 8

要从 a 获取&dyn Ta Box<dyn T>,请使用&*

let c: &dyn MyTrait = &*b;
Run Code Online (Sandbox Code Playgroud)

*用于将框取消引用到其内容 ( dyn MyTrait),然后&用于将其作为引用。


这也是&Foo从 a获取 a 的“正确”方法Box<Foo>。适用于具体类型的原因&b是因为该Deref特征允许&Box<T>强制&T

如果 T 实现 Deref<Target = U>,并且 x 是 T 类型的值,则:

  • &T 类型的值被强制转换为 &U 类型的值

它不适用于特征对象的原因是,它&dyn MyTrait 可能有效&Box<...>,并且即使失败也不会尝试强制转换。