Rust Trait 对象转换 [英] Rust Trait object conversion

查看:36
本文介绍了Rust Trait 对象转换的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

由于此错误的两个实例,以下代码将无法编译:

The following code won't compile due to two instances of this error:

error[E0277]: trait bound Self: std::marker::Sized 不满足

error[E0277]: the trait bound Self: std::marker::Sized is not satisfied

我不明白为什么在这种情况下需要 Sized 因为 &self&Any 都是指针和操作不需要知道实现 trait 的结构的大小,它只需要知道指针本身和它正在转换的类型,因为 &self 是通用的当在 trait 中实现时.

I don't understand why Sized is required in this instance as both &self and &Any are pointers and the operation does not require knowledge of the size of the structure that implements the trait, it only requires knowledge of the pointer itself and the type it is converting from and to, which it will have because &self is generic when implemented inside a trait.

我认为这可能是编译器强制执行不必要约束的一个实例,我已经考虑向 rust-lang GitHub 存储库提交问题,但我想我应该在我走之前看看这里是否有人知道我不知道的事情提出问题.

I think this may be an instance of the compiler enforcing unnecessary constraints and I've considered filing an issue with the rust-lang GitHub repo but I figured I should probably see if someone here knows something I don't before I go file an issue.

use std::any::Any;

trait Component: Any {
    fn as_any(&self) -> &Any {
        self
    }

    fn as_any_mut(&mut self) -> &mut Any {
        self
    }
}

替代方法是为实现此特征的结构体制作 as_any()as_any_mut() 所需的函数,但对于这些结构体,实现始终是与此处显示的每个字符完全一样,从而产生多个相同样板代码的实例.

The alternative to this is to make as_any() and as_any_mut() required functions for the structs that implement this trait, but for those structures the implementation would always be exactly as displayed here down to each individual character, resulting in several instances of identical boilerplate code.

推荐答案

我发现我认为是一个很棒的解决方案,它不需要新的编译器功能.

I found what I consider to be a great solution that didn't require new compiler features.

pub trait Component {
    // ...
}

pub trait ComponentAny: Component + Any {
    fn as_any(&self) -> &Any;
    fn as_any_mut(&mut self) -> &mut Any;
}

impl<T> ComponentAny for T
    where T: Component + Any
{
    fn as_any(&self) -> &Any {
        self
    }

    fn as_any_mut(&mut self) -> &mut Any {
        self
    }
}

从这里开始,我只是将所有 API 更改为接受 ComponentAny 而不是 Component.因为 Any 是为任何 'static 类型自动实现的,所以 ComponentAny 现在可以为任何 'static 类型自动实现实现 Component.感谢 有没有办法结合多个特征来定义一个新的特征?对于这个想法.

From here, I just change all my APIs to accept ComponentAny instead of Component. Because Any is automatically implemented for any 'static type, ComponentAny is now automatically implemented for any 'static type that implements Component. Thanks to Is there a way to combine multiple traits in order to define a new trait? for the idea.

这篇关于Rust Trait 对象转换的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆