Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

rust:copy & move #55

Open
hello2dj opened this issue Sep 12, 2019 · 0 comments
Open

rust:copy & move #55

hello2dj opened this issue Sep 12, 2019 · 0 comments

Comments

@hello2dj
Copy link
Owner

hello2dj commented Sep 12, 2019

move & copy

什么是 move? 什么又是 copy 呢?

  1. copy

    我们以一个好理解的角度入手:那就是我们平时使用的快捷键 Ctrl+C & Ctrl+V 这个就是copy
    image

    如上图 从 a 位置 Ctrl+C 在 b 位置 Ctrl+V,于是 b 位置也有 'C'。原来的 'C',我们还可以继续操作。这个过程就是个 copy。这个叫先感性的理解一下啥是 copy,就是依据一个东西再造一个一模一样的出来,这两个东西共存。3D 打印,完美的 copy。

    那对于 rust 来说 copy 是啥呢?

    1. copy 的语义表现

      资源:可以简单的理解为变量

      将资源 copy 以后,原资源可以继续使用,copy 的新资源也可以使用。

    let a = 32;
    let b = a; // copy
    
    println!("a: {}, b: {}", a, b); // a, b 都可以使用

    我一步一步来分析,看一个最简单的 copy 的使用场景

    let a: i32 = 23;

    上面的一个表达式语句给了我们哪些信息呢?

    • 声明了一个 变量 a
    • a 的类型是 i32
    • a 是不可变的
    • a 的值 是 23
    • a 在栈上分配
    • a 占用的内存大小是 4 个字节
    let a: i32 = 23;
    let b = a;

    这个例子又多了一条表达式语句,那多出来的那条又给了我们什么信息呢?

    • 声明了一个 变量 b

    • b 的类型是 i32

    • b 是不可变的

    • b 在栈上分配

    • b 占用的内存大小是 4 个字节

    • b 的值呢? 肯定是 23

    b 的值 是 23,那 a 的值是如何赋值给 b 的呢?copy 按位 copy 。
    image

    0x00 的内容是 a 的内容,当我们赋值的时候 就会 把 0x00 的内容直接 copy 到 0x02 ( Ctrl+c & Ctrl+v ),这样就完成了 rust 中的一次赋值,也会是 copy。

    1. copy 语义的实现细节: copy by bits

      要解释按位 copy 就需要用到复合类型。

      上面我们讲了 i32 基本类型发生 copy 的场景,接下来我们看看复合类型的copy。

      // 不包含引用的复合类型
      #[derive(Copy, Clone)] // 需要明确这个复合类型可以 copy
      struct A {
      	x: i32,
      	y: i32,
      }
      let a = A { x: 32, y: 34 };
      let b = a; // copy

image

       //  包含引用类型
       #[derive(Copy, Clone)] // 需要明确这个复合类型可以 copy
       struct A<'a> {
     	x: i32,
     	y: &'a i32,
       }
       let y = 377; 
       let a = A { x: 32, y: &y };
       let b = a; // copy

image

     按位 copy 的要点来了,b 的 y 值也是 0x00,并不会 把 y 引用的内容也 copy 一遍。
  1. copy 语义的发生场景

    copy 会发生在以下场景中

  • 变量赋值

    let a = b; // copy
  • 函数传参

    fn say(word: i32) {}
    
    let c = 32;
    
    say(c); // copy
  • 函数返回值

    fn give_you() -> i32 {
    	return 23;
    }
  • 模式匹配 match

    struct A {
    	i: i32
    };
    
    let a = A { i: 32 };
    
    match a {
    	A {i} => println!("###, {}", i); // copy
    };
  • 模式匹配 let

    struct A {
    	i: i32
    };
    
    let a = A { i: 32 };
    
    let A { i: x }  = a; // copy
  • 闭包 capture

    let a = 32;
    let c = vec![1,2,3,4];
    let d: Vec<i32> = c
    	.iter()
    	.map(|v| v + a) // copy a
    	.collect();
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

1 participant