例如:
impl<T: ?Sized> cmp::Eq for $t<T> {}
Run Code Online (Sandbox Code Playgroud)
如果没有实现,为什么还要编写这段代码呢?它发生在很多地方,特别是与方程式有关的地方。
#[unstable(feature = "structural_match", issue = "31434")]
impl<T: ?Sized> StructuralPartialEq for $t<T> {}
#[unstable(feature = "structural_match", issue = "31434")]
impl<T: ?Sized> StructuralEq for $t<T> {}
#[stable(feature = "rust1", since = "1.0.0")]
impl<T: ?Sized> Copy for $t<T> {}
impl<T: ?Sized> !Freeze for UnsafeCell<T> {}
unsafe impl<T: ?Sized> Freeze for PhantomData<T> {}
unsafe impl<T: ?Sized> Freeze for *const T {}
unsafe impl<T: ?Sized> Freeze for *mut T {}
unsafe impl<T: ?Sized> Freeze for &T {}
unsafe impl<T: ?Sized> Freeze for &mut T {}
Run Code Online (Sandbox Code Playgroud)
特征可以用空来实现impl {}没有方法,或者它的所有方法都有默认实现,则可以使用空块来实现特征。这些被称为“标记”或“标签”特征。
无开销的抽象:Rust 中的特征有标记特征的描述:
\n\n\nRust 有一些对类型进行分类的“标记”:
\nSend、Sync、Copy、Sized。这些标记只是具有空体的特征,然后可以在泛型和特征对象中使用。标记可以在库中定义,并且它们自动提供-style 实现:例如,#[derive]如果所有 a 类型组件都是,那么该类型也是。Send正如我们之前所看到的,这些标记可能非常强大:Send标记是 Rust 保证线程安全的方式。
Eq是另一个常见的标记特征。它是已经实现的类型的标签PartialEq,表明相等操作实际上不是“部分”的;它是完全自反、对称和传递的。实现它不需要任何额外的实现,因为eq实现是从类型的impl PartialEq { ... }块中获取的。
\n\nRun Code Online (Sandbox Code Playgroud)\npub trait Eq: PartialEq<Self> { }\n等价比较的特征是等价关系。
\n这意味着,除了
\na == b和a != b是严格逆元之外,相等性还必须是(对于所有a,b和c):\n
\n- 自反:a == a;
\n- 对称:a == b 意味着 b == a;和
\n- 传递性: a == b 和 b == c 意味着 a == c。\n编译器无法检查此属性,因此
\nEq意味着PartialEq,并且没有额外的方法。可衍生的
\n该特性可以与 一起使用
\n#[derive]。派生时,由于Eq没有额外的方法,它只是通知编译器这是一个等价关系而不是部分等价关系。请注意,该derive策略要求所有字段都是Eq,这并不是\xe2\x80\x99 总是需要的。我该如何实施
\nEq?如果您无法使用该
\nderive策略,请指定您的类型实现Eq,它没有方法:Run Code Online (Sandbox Code Playgroud)\nenum BookFormat { Paperback, Hardback, Ebook }\nstruct Book {\n isbn: i32,\n format: BookFormat,\n}\nimpl PartialEq for Book {\n fn eq(&self, other: &Self) -> bool {\n self.isbn == other.isbn\n }\n}\nimpl Eq for Book {}\n