如何实现Rust的Copy trait?

89

我正在尝试在Rust中初始化一个结构体数组:

enum Direction {
    North,
    East,
    South,
    West,
}

struct RoadPoint {
    direction: Direction,
    index: i32,
}

// Initialise the array, but failed.
let data = [RoadPoint { direction: Direction::East, index: 1 }; 4]; 

当我尝试编译时,编译器抱怨Copy特性未被实现:

error[E0277]: the trait bound `main::RoadPoint: std::marker::Copy` is not satisfied
  --> src/main.rs:15:16
   |
15 |     let data = [RoadPoint { direction: Direction::East, index: 1 }; 4]; 
   |                ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ the trait `std::marker::Copy` is not implemented for `main::RoadPoint`
   |
   = note: the `Copy` trait is required because the repeated element will be copied

如何实现 Copy 特质?


8
#[derive(Clone, Copy)]是正确的方式,但需要说明的是,它并不神奇:手动实现这些特性很容易,尤其是像你这样简单的情况: impl Copy for Direction {} impl Clone for Direction { fn clone(&self) -> Self { *self } } - user395760
2个回答

118

您不需要自己实现Copy; 编译器可以为您派生它:

#[derive(Copy, Clone)]
enum Direction {
    North,
    East,
    South,
    West,
}

#[derive(Copy, Clone)]
struct RoadPoint {
    direction: Direction,
    index: i32,
}

请注意,实现了 Copy 的每种类型都必须实现 CloneClone 也可以被派生。


2
为什么需要“Clone”?如果想要实现复制,是否总是需要添加它? - xetra11
14
是的,CloneCopy的超级trait,因此每个实现Copy的类型也需要实现Clone - fjh
5
这不完全是一个答案,但我更喜欢派生Clone而不是派生Copy。这允许开发人员明确地在元素上执行.clone()操作,但它不会为您执行此操作(这是Copy的工作)。因此,Clone至少有存在于Copy之外的理由;我认为Clone实现该方法,但Copy使其自动化,两者之间没有冗余。 - zeh

23

在你的枚举类型之前添加#[derive(Copy, Clone)]即可。

如果你真的想要,也可以

impl Copy for MyEnum {}
< p > derive-attribute 在幕后执行相同的操作。 < /p >

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接