Copy and clone a custom struct

Hi, I am trying to create a copy implementation to a structure with Array2D and a simple array. The compiler doesn't like my implementation. Thanks for any help. Mor

struct Cube1
{
    pub s1: Array2D<i32>,
    pub s2: Array2D<i32>,
    pub s3: Array2D<i32>,
    pub s4: Array2D<i32>,
    pub s5: Array2D<i32>,
    pub s6: Array2D<i32>,
    pub s1_sides: [i32; 4],
    pub s2_sides: [i32; 4],
    pub s3_sides: [i32; 4],
    pub s4_sides: [i32; 4],
    pub s5_sides: [i32; 4],
    pub s6_sides: [i32; 4],
}

impl Copy for Cube1
{
    fn copy(&self) -> Cube1 {
        return Cube1 {
            s1: Array2D::from_rows(self.s1.as_rows()),
            s2: Array2D::from_rows(self.s2.as_rows()),
            s3: Array2D::from_rows(self.s3.as_rows()),
            s4: Array2D::from_rows(self.s4.as_rows()),
            s5: Array2D::from_rows(self.s5.as_rows()),
            s6: Array2D::from_rows(self.s6.as_rows()),
            s1_sides: self.s1_sides,
            s2_sides: self.s2_sides,
            s3_sides: self.s3_sides,
            s4_sides: self.s4_sides,
            s5_sides: self.s5_sides,
            s6_sides: self.s6_sides,
        }
    }
}

The error I am getting:

   |
31 | /     fn copy(&self) -> Cube1 {
32 | |         return Cube1 {
33 | |             s1: Array2D::from_rows(self.s1.as_rows()),
34 | |             s2: Array2D::from_rows(self.s2.as_rows()),
...  |
45 | |         }
46 | |     }
   | |_____^ not a member of trait `Copy`



error[E0204]: the trait `Copy` may not be implemented for this type
  --> src\cube.rs:29:6
   |
15 |     pub s1: Array2D<i32>,
   |     -------------------- this field does not implement `Copy`
16 |     pub s2: Array2D<i32>,
   |     -------------------- this field does not implement `Copy`
17 |     pub s3: Array2D<i32>,
   |     -------------------- this field does not implement `Copy`
18 |     pub s4: Array2D<i32>,
   |     -------------------- this field does not implement `Copy`
19 |     pub s5: Array2D<i32>,
   |     -------------------- this field does not implement `Copy`
20 |     pub s6: Array2D<i32>,
   |     -------------------- this field does not implement `Copy`
...
29 | impl Copy for Cube1
   |      ^^^^

The Copy trait has no methods: it is a marker trait used by the compiler not to invalidate "old values" on "move", which are implemented as shallow bit-wise copies.

The Clone trait is the one where you can override the "copying" behavior, but only do that if you are not implementing Copy already (since when something is Copy (and thus Clone), it is expected that Clone simply delegate to Copy).

  • The error message:

    suggests that you won't be able to implement Copy, since for that to be doable, each and every field needs to be, in and of itself, Copy. That's where Clone would shine, though.

The clone worked but that mean that I have to do: let d = c.clone();
instead of doing: let d = c;

But if c can't be copied, because it contains fields that can't be copied, why would you expect that

would somehow magically copy it?

I thought that I can implement a copy function like I did for the clone.

Thanks for the help

1 Like

In addition to Copy meaning "a shallow bit for bit copy" as @Yandros said, you can think of this restriction as "no implicit non-Copy clones". Implicit clones would interact poorly with the ownership model.

// Hopefully I don't .clone() because I'm just trying to move ownership!
struct.frob = complicated_thing;

(And Rust tends to prefer potentially expensive operations be explicit to boot.)

1 Like