rust入门笔记二 所有权

rust入门笔记二 所有权,第1张

1.Ownership是Rust的一个核心概念。
引用:类似于函数传值
借用:类似于函数传引用
每种编程语言都有自己的一套内存管理的方法。有些需要显式的分配和回收内存(如C),有些语言则依赖于垃圾回收器来回收不使用的内存(如Java)。而Rust不属于以上任何一种,它有一套自己的内存管理规则,叫做Ownership。

Rust中常规数据类型,其数据都是存储在栈中,而像String或一些自定义的复杂数据结构(我们以后会对它们进行详细介绍),其数据则存储在堆内存中。

  1. Ownership的规则
    Rust的所有权并不难理解,它有且只有如下三条规则:

在Rust中,每一个值都有对应的变量,这个变量称为值的owner
一个值在某一时刻只能有一个owner
当owner超出作用域后,值会被销毁

  1. 变量作用域
    Ownership的规则中,有一条是owner超过范围后,值会被销毁。那么owner的范围又是如何定义的呢?在Rust中,花括号通常是变量范围作用域的标志。最常见的在一个函数中,变量s的范围从定义开始生效,直到函数结束,变量失效。
fn main() {            // s is not valid here, it’s not yet declared
    let s = "hello";   // s is valid from this point forward

    // do stuff with s
}                      // this scope is now over, and s is no longer valid

  1. Ownership的移动
    前面我们提到,花括号通常是变量作用域隔离的标志(即Ownership失效)。除了花括号以外,还有其他的一些情况会使Ownership发生变化,先来看两段代码。
let x = 5;
let y = x;
println!("x: {}", x);

let s1 = String::from("hello");
let s2 = s1;
println!("s1: {}", s1);

``
对于第二段代码我们想象中,也可以是这样的过程,但实际上Rust并不是这样做的。先来说原因:对于较大的对象来说,这样的复制是非常浪费空间和时间的。那么Rust中实际情况是怎么样呢?`
Rust为了解决这一问题,在执行let s2 = s1;这句代码时,认为s1已经超出了作用域,即右侧的内容的owner已经变成了s2,也可以说s1的ownership转移给了s2。也就是下图所示的情况。
![在这里插入图片描述](https://img-blog.csdnimg.cn/a3c2b4dfaed146f181d319843eb7bfa1.png)
另一种实现:clone
如果你确实需要深度拷贝,即复制堆内存中的数据。Rust也可以做到,它提供了一个公共方法叫做clone。

```rust
let s1 = String::from("hello");
let s2 = s1.clone();

println!("s1 = {}, s2 = {}", s1, s2);

5.引用
引用:类似于函数传值

// fn reverse_string(s: String) ->(String, String){
//     (s.clone(), s.chars().rev().collect())
// }
fn reverse_string(s: &String) ->String{
    s.chars().rev().collect()
}
fn main(){
    let s1 = String::from("any string");
    let s2 = reverse_string(&s1); //传引用,不会获取所有权
    println!("{} {}", s1,s2)
    // println!("{} {}", s1_clone,s2)


    // let data1 = String::from("Hello");
    // let data2 = 444.to_string();
    // println!("Say: {} {}", data1,data2);
}

6.借用
可变引用
借用:类似于函数传引用

fn append_string(s:&mut String){ //&表示引用地址
    s.push_str("!")
}
fn main(){
    let mut s = String::from("any string");
    append_string(&mut s);
    println!("{}", s);

}

参考视频
参考内容

欢迎分享,转载请注明来源:内存溢出

原文地址: http://outofmemory.cn/langs/799806.html

(0)
打赏 微信扫一扫 微信扫一扫 支付宝扫一扫 支付宝扫一扫
上一篇 2022-05-06
下一篇 2022-05-06

发表评论

登录后才能评论

评论列表(0条)

保存