rust 有没有一种方法可以得到一个(de)Serializable版本的Box< dyn Any>?

r1wp621o  于 2023-08-05  发布在  其他
关注(0)|答案(2)|浏览(104)

我在一个预先存在的项目工作,需要添加一个字段结构Message这是一个Box <dyn Any>
对于这个项目,将Box<dyn Any>转换为枚举是不可能的。

pub struct Message<PB: ProtocolBehavior> {
    /* */
    pub info: Box<dyn Any>,
}

字符串
不幸的是,Message需要是(反)序列化的,并实现哈希,克隆,调试,显示(列表还在继续);因此,字段info也是如此。
我想出来的是创建一个新的trait AnySerializable。我让它实现了所有必要的特性。(感谢dtolnay's typetag crate,我能够使这个新的trait序列化)

#[typetag::serde(tag = "type")]
pub trait AnySerializable: Any + core::fmt::Debug + std::fmt::Display + DynClone + DynHash {}


然后我修改了Message的字段info

pub struct Message<PB: ProtocolBehavior> {
    /* */
    pub info: Box<dyn AnySerializable>,
}


但是,我需要能够将信息转换为Box<dyn Any>
下面的代码给了我一个错误,因为返回类型不匹配。

impl Message {
    pub fn get_info(&self) -> Box<dyn Any> {
        self.info
    } 
}


然后我尝试在trait AnySerializable中添加一个方法

#[typetag::serde(tag = "type")]
pub trait AnySerializable: Any + core::fmt::Debug + std::fmt::Display + DynClone + DynHash {
    fn as_any(&self) -> dyn Any;
}


沿着用于Message的该方法。

impl Message {
    pub fn get_info(&self) -> Box<dyn Any> {
        Box::new(self.info.clone().as_ref().as_any())
    } 
}


但是我不能装箱dyn Any,因为在编译时它的大小是未知的。
但我想做这样的事。有没有一种方法可以做到这一点,可能是不安全的Rust?
我尝试在项目中将任何出现的Any替换为AnySerializable,但我得到了额外的错误,这些错误似乎非常复杂。如果我不能优雅地得到一个Box<dyn Any>,我会调查他们。

f4t66c6m

f4t66c6m1#

cannot currently upcast在稳定生 rust ,甚至不使用不安全的[0][1]。注意:上转换是将子trait对象(AnySerializable)转换为它的supertrait对象(Any)。
恐怕对您来说最好的方法是将许多Any的出现改为AnySerializable。在nightly rust中有一个特性,它允许在最小的代码更改下工作,但根据它的进展,我不希望它在接下来的几个版本中稳定下来。

#![feature(trait_upcasting)]

use std::any::Any;

trait AnySerializable: Any {
    fn serialize(&self) -> String;
}

impl<T:Any> AnySerializable for T {
    fn serialize(&self) -> String {"".to_string()}
}

fn main() {
    let serializable: Box<dyn AnySerializable> = Box::new(());
    let any: Box<dyn Any> = serializable as Box<dyn Any>;
}

字符串
[0][Why doesn't Rust support trait object upcasting?](https://stackoverflow.com/questions/28632968/why-doesnt-rust-support-trait-object-upcasting)的
[1][Is it possible to cast a trait object to another trait object?](https://stackoverflow.com/questions/55895583/is-it-possible-to-cast-a-trait-object-to-another-trait-object)的

yi0zb3m4

yi0zb3m42#

我找到了这个板条箱,它做的正是我想做的!
它允许向下转换为Box<dyn Any>

相关问题