#traits #dyn #object #safe #type

对象安全

为特例对象实现对象不安全特例

4 个版本 (2 个破坏性更新)

0.3.1 2023年8月17日
0.3.0 2023年8月8日
0.2.0 2023年8月4日
0.1.0 2023年8月3日

#2217Rust 模式

MIT/Apache

17KB
304

对象安全

您需要以 dyn MyTrait 的形式使用特例对象,这些对象实现了非对象安全的特例吗?

这个软件包通过提供与一些常用的非对象安全特例类似的、对象安全的特例,并自动为广泛的类型实现这些特例来解决此问题。目前支持以下特例

  • Hash
  • PartialEq
  • Eq

我计划将此支持扩展到其他特例,并提供宏来简化自定义特例的过程。

了解对象安全:[链接](https://doc.rust-lang.net.cn/reference/items/traits.html#object-safety)

示例

Hash 特例为例。 Hash 不是对象安全的,这意味着在 Rust 中 dyn Hash 不是一个有效的类型。现在,想象一下您定义了以下自定义特例

pub trait MyTrait: Hash {}

由于 MyTrait 扩展了 Hash,它也不是对象安全的,因此 dyn MyTrait 不是一个有效的类型。这个软件包提供了一种绕过这种限制的方法,因此您可以使用对象安全的特例,其对象实现了如 Hash 这样的对象不安全特例。

Hash 作为特例约束,而不是将 HashObj 作为特例约束。

pub trait MyTrait: HashObj {}

您不需要实现 HashObj。它将自动为任何实现了 Hash 的类型实现。现在,dyn MyTrait 是对象安全的。如果想要 dyn MyTrait 实现 Hash,只需添加一行代码即可。

impl_hash(dyn MyTrait);

以下是 HashObj 所具有的所有特征

  • 任何实现了 Hash 的类型自动实现 HashObj
  • dyn HashObj 实现 Hash
  • Obj<T> 为任何将解引用到实现 HashObj 的类型的 T 实现了 Hash
  • impl_hash 可以实现 Hash 接口,适用于任何实现了 HashObj 的类型,例如一个 trait 对象 dyn MyTrait,其中 MyTrait 是一个扩展 HashObj 的 trait。
impl_hash! {
    // typical use, where MyTrait: HashObj
    dyn MyTrait,
    dyn AnotherTrait,

    // structs and enums are supported if they deref to
    // a target that implements HashObj or Hash.
    MyStruct,

    // special syntax for generics.
    MySimpleGeneric<T> where <T>,
    MyGenericType<T, F> where <T, F: HashObj>,
    dyn MyGenericTrait<T> where <T: SomeTraitBound>,

    // the actual impl for Obj
    Obj<T> where <T: Deref<Target=X>, X: HashObj + ?Sized>,
}

无运行时依赖