如何编写知道实现者为[u8]的特征方法?

我正在为&[u8]实现特征,但是我不能在特征实现中使用self。我以为trait无法检测到类型,我应该使用where子句,但是我不知道没有实现者怎么使用它。

use std::fmt::Debug;

pub trait Xor: Debug {
    fn xor(&self,key_bytes: &[u8]) -> &[u8] {
        for n in &self[..] {
            dbg!(n);
        }
        unimplemented!()
    }
}

impl Xor for [u8] {}

fn main() {
    let xa = b"1234";
    xa.xor(b"123");
}

Playground

error[E0608]: cannot index into a value of type `&Self`
 --> src/main.rs:5:19
  |
5 |         for n in &self[..] {
  |                   ^^^^^^^^
asdff_px 回答:如何编写知道实现者为[u8]的特征方法?

您可以在两个地方编写特征方法的正文:

  • 在性状本身中,作为提供的方法
  • impl块中。

如果未提供方法,则需要 ,这意味着所有实现者都必须在适当的impl块中编写自己的主体。

提供的方法只能使用特征的实现者所有共有的属性,这意味着您只能使用其他特征方法或超特征方法(例如: Debug)。但是impl块中的方法可以使用特定于实现特征的类型的属性。您想使用特定于[u8]的内容-通过[..]进行索引编制-因此xor应该是必需的方法:

pub trait Xor {
    fn xor(&self,key_bytes: &[u8]) -> &[u8];
}

impl Xor for [u8] {
    fn xor(&self,key_bytes: &[u8]) -> &[u8] {
        for n in &self[..] {
            dbg!(n);
        }
        unimplemented!()
    }
}

为方便起见,提供的方法通常仅使用具有相同特征的其他方法,例如Iterator上的大多数方法(请参见Why don't we implement all the functions from Iterator to implement an iterator?)。

  

是否可以为几种类型实现特征(无需编写多个impl块)?

是的,如果某个特征公开了您将用来编写Xor的功能,则可以使用该特征来编写通用的impl。例如,String[u8]都实现AsRef<[u8]>,因此您可以使用它来编写同时适用于两者的impl

impl<T: ?Sized + AsRef<[u8]>> Xor for T {
    fn xor(&self,key_bytes: &[u8]) -> &[u8] {
        for n in &self.as_ref()[..] {
            dbg!(n);
        }
        unimplemented!()
    }
}

Playground link.

另请参见

本文链接:https://www.f2er.com/3160023.html

大家都在问