繁体   English   中英

什么时候我不应该实现引用该特征的实现者的特征?

[英]When should I not implement a trait for references to implementors of that trait?

如果我有一个特征,并且接受一个约束到该类型的泛型类型的函数,一切正常。 如果我尝试传入对该类型的引用,我会收到编译错误。

trait Trait {
    fn hello(&self) -> u32;
}

struct Struct(u32);

impl Trait for Struct {
    fn hello(&self) -> u32 {
        self.0
    }
}

fn runner<T: Trait>(t: T) {
    println!("{}", t.hello())
}

fn main() {
    let s = Struct(42);

    // Works
    runner(s);

    // Doesn't work
    runner(&s);
}
error[E0277]: the trait bound `&Struct: Trait` is not satisfied
  --> src/main.rs:24:5
   |
24 |     runner(&s);
   |     ^^^^^^ the trait `Trait` is not implemented for `&Struct`
   |
   = help: the following implementations were found:
             <Struct as Trait>
note: required by `runner`
  --> src/main.rs:13:1
   |
13 | fn runner<T: Trait>(t: T) {
   | ^^^^^^^^^^^^^^^^^^^^^^^^^

我可以通过为实现特征的类型的任何引用实现特征来解决问题:

impl<'a, T> Trait for &'a T
where
    T: Trait,
{
    fn hello(&self) -> u32 {
        (*self).hello()
    }
}

我遗失的那条信息是什么时候不应该实现这个? 问另一种方式,为什么编译器不会自动为我实现这个? 由于目前没有,我认为必须存在这种实施方式不利的情况。

什么时候不应该实现这个? 问另一种方式,为什么编译器不会自动为我实现这个? 由于目前没有,我认为必须存在这种实施方式不利的情况。

举个例子,我们立刻想到了Default特质。

pub trait Default {
    fn default() -> Self;
}

我可以为T实现它,但是没有办法为&T自动实现它。

您在此处撰写的特定特征仅通过引用self ,这是可以编写您执行的其他实现的唯一原因。

因此,将参数设置为runner()的值可能是不合需要的; 你应该参考它。 本指南一般可以适用:如果可以实现特征参考,而不是想知道“我应该实现它吗?”你应该想知道“我为什么实现它?”因为你应该使用它的唯一情况应该是首先要改变以通过引用获取对象。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM