< 返回版块

Snowmanzzz 发表于 2023-03-24 17:09

编译期的报错信息是 cannot move out of *allergen which is behind a shared reference move occurs because *allergen has type Allergen, which does not implement the Copy trait

代码如下


use self::Allergen::*;


#[derive(Debug, PartialEq, Eq)]
pub enum Allergen {
    Eggs = 1 << 0,
    Peanuts = 1 << 1,
    Shellfish = 1 << 2,
    Strawberries = 1 << 3,
    Tomatoes = 1 << 4,
    Chocolate = 1 << 5,
    Pollen = 1 << 6,
    Cats = 1 << 7,
}

const ALLERGENS: [Allergen; 8] =
    [Eggs, Peanuts, Shellfish, Strawberries, Tomatoes, Chocolate, Pollen, Cats];

pub struct Allergies {
    allergens: u32,
}

impl Allergies {
    pub fn new(n: u32) -> Self {
        Allergies { allergens: n }
    }

    pub fn is_allergic_to(&self, allergen: &Allergen) -> bool {
        let allergen = *allergen as u32;
        self.allergens & allergen == allergen
    }

    pub fn allergies(&self) -> Vec<Allergen> {
        unimplemented!("Return the list of allergens contained within the score with which the Allergies struct was made.");
    }
}

我觉得很神奇的是给pub enum Allergen加了 derive copy clone就能干掉报错

为什么呢?

评论区

写评论
作者 Snowmanzzz 2023-03-25 00:35

你是贺老师么hhh

--
👇
hax10: let allergen = *allergen as u32;

在这行,你新建的变量allergen将复制原来allergen引用所指的值。因此,这个值的类型必须实现Copy特征,不然编译器不知道怎么进行复制。

Copy特征的实现就是通过derive命令而自动生成的,Rust不允许你手动实现Copy。另外,Rust也要求所有实现Copy特征的类型同时实现Clone。克隆和复制的区别在于复制仅仅会把原数据的字节拷到新变量里头,但是克隆能调用你自己手写的克隆函数。

hax10 2023-03-24 21:10

let allergen = *allergen as u32;

在这行,你新建的变量allergen将复制原来allergen引用所指的值。因此,这个值的类型必须实现Copy特征,不然编译器不知道怎么进行复制。

Copy特征的实现就是通过derive命令而自动生成的,Rust不允许你手动实现Copy。另外,Rust也要求所有实现Copy特征的类型同时实现Clone。克隆和复制的区别在于复制仅仅会把原数据的字节拷到新变量里头,但是克隆能调用你自己手写的克隆函数。

作者 Snowmanzzz 2023-03-24 20:12

copy clone就是同名trait约束么,做什么的呢?

--
👇
Mike Tang: 自动实现了同名trait约束。

Mike Tang 2023-03-24 18:37

自动实现了同名trait约束。

1 共 4 条评论, 1 页