Rust权威指南学习笔记——认识所有权

什么是所有权

1. 所有权规则

  • Rust中的每一个值都有一个对应的变量作为它的所有者。
  • 在同一时间内,值有且仅有一个所有者。
  • 当所有者离开自己的作用域时,它持有的值就会被释放掉。

2. 变量作用域

  • s在进入作用域后变得有效。
  • 它会保持自己的有效性直到自己离开作用域为止。

Rust在变量离开作用域时,会调用一个叫作drop的特殊函数。

3.移动

为了确保内存安全,同时也避免复制分配的内存,Rust在这种场景下会简单地将s1废弃,不再视其为一个有效的变量。因此,Rust也不需要在s1离开作用域后清理任何东西。

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

4. 克隆:深拷贝

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

5. Copy的trait

let x = 5;
let y = x; println!("x = {}, y = {}", x, y);
// x = 5, y = 5

以上代码没有调用clone,x在被赋值给y后也依然有效,且没有发生移动现象。这是为什么?

  • 一旦某种类型拥有了Copy这种trait,那么它的变量就可以在赋值给其他变量之后保持可用性。
  • 如果一种类型本身或这种类型的任意成员实现了Drop这种trait,那么Rust就不允许其实现Copy这种trait。
  • 一些拥有Copy trait的类型
    • 所有的整数类型,诸如u32。
    • 仅拥有两种值(true和false)的布尔类型:bool。
    • 字符类型:char。
    • 所有的浮点类型,诸如f64。
    • 如果元组包含的所有字段的类型都是Copy的,那么这个元组也是Copy的。例如,(i32, i32)是Copy的,但(i32, String)则不是。

引用与借用

(1)引用

let s1 = String::from("hello");

let len = calculate_length(&s1);

...

fn calculate_length(s: &String) -> usize { // s 是一个指向 String 的引用
s.len()
} // 到这里,s离开作用域。但是由于它并不持有自己所指向值的所有权,
//所以没有什么特殊的事情会发生
  • 这些&代表的就是引用语义,它们允许你在不获取所有权的前提下使用值。
  • 与变量类似,引用是默认不可变的,Rust不允许我们去修改引用指向的值。以下编译出错。
fn main() {
let s = String::from("hello"); change(&s);
} fn change(some_string: &String) {
some_string.push_str(", world");
}

(2)可变引用

  • 首先,我们需要将变量s声明为mut,即可变的。其次,我们使用&mut s来给函数传入一个可变引用,并将函数签名修改为some_string: &mut String来使其可以接收一个可变引用作为参数。
fn main() {
let mut s = String::from("hello"); change(&mut s);
} fn change(some_string: &mut String) {
some_string.push_str(", world");
}
  • 对于特定作用域中的特定数据来说,一次只能声明一个可变引用。

cannot borrow 's' as mutable more than once at a time...

let mut s = String::from("hello"); 

let r1 = &mut s;
let r2 = &mut s;

好处:避免数据竞争。

数据竞争(data race)与竞态条件十分类似,它会在指令满足以下3种情形时发生:

• 两个或两个以上的指针同时访问同一空间。

• 其中至少有一个指针会向空间中写入数据。

• 没有同步数据访问的机制。

(3)悬垂引用

使用拥有指针概念的语言会非常容易错误地创建出悬垂指针。这类指针指向曾经存在的某处内存地址,但该内存已经被释放掉甚至是被重新分配另作他用了。而在Rust语言中,编译器会确保引用永远不会进入这种悬垂状态。假如我们当前持有某个数据的引用,那么编译器可以保证这个数据不会在引用被销毁前离开自己的作用域。

切片

《Rust权威指南》学习笔记——4. 认识所有权的更多相关文章

  1. HTTP权威指南-学习笔记

    目录 HTTP权威指南-学习笔记 HTTP: Web的基础 URL与资源 HTTP报文 连接管理 HTTP结构 Web服务器 代理 缓存 集成点: 网关,隧道及中继 Web机器人 识别,认证与安全 客 ...

  2. JavaScript 权威指南-学习笔记(一)

    本文所有教程及源码.软件仅为技术研究.不涉及计算机信息系统功能的删除.修改.增加.干扰,更不会影响计算机信息系统的正常运行.不得将代码用于非法用途,如侵立删! ## JavaScript 权威指南-学 ...

  3. CSS权威指南学习笔记系列(1)CSS和文档

    题外话:HTML是一种结构化语言,而CSS是它的补充:这是一种样式语言.CSS是前端三板斧之一,因此学习CSS很重要.而我还是菜鸟,所以需要加强学习CSS.这个是我学习CSS权威指南的笔记,如有不对, ...

  4. Hadoop权威指南学习笔记二

    MapReduce简单介绍 声明:本文是本人基于Hadoop权威指南学习的一些个人理解和笔记,仅供学习參考,有什么不到之处还望指出,一起学习一起进步. 转载请注明:http://blog.csdn.n ...

  5. Hadoop权威指南学习笔记一

    Hadoop简单介绍 声明:本文是本人基于Hadoop权威指南学习的一些个人理解和笔记,仅供学习參考,有什么不到之处还望指出.一起学习一起进步. 转载请注明:http://blog.csdn.net/ ...

  6. Hadoop权威指南学习笔记三

    HDFS简单介绍 声明:本文是本人基于Hadoop权威指南学习的一些个人理解和笔记,仅供学习參考.有什么不到之处还望指出,一起学习一起进步. 转载请注明:http://blog.csdn.net/my ...

  7. IDA Pro权威指南学习笔记(一)

    一直不懂逆向,最近刚好不忙,于是学习逆向,用来做笔记,顺便和大家分享交流. 参考书籍<IAD PRO权威指南> 工具: PETools: ETools 是另一款很好的PE文件编辑工具,以前 ...

  8. css权威指南学习笔记 —— css选择器

    1,选择器:选择器的一些基本常用规则基本都记得,w3c上都有,平时也常用,不常用的一些后代选择器经常就忘记了.一些归纳一下后代选择器,加深一下印象: a:子选择器:   p>a  a是直接是p的 ...

  9. maven权威指南学习笔记(五)—— POM

    1. 简介 Archetype插件通过 pom.xml 文件创建了一个项目.这就是项目对象模型 (POM),一个项目的声明性描述. 当Maven运行一个目标的时候,每个目标都会访问定 义在项目POM里 ...

  10. maven权威指南学习笔记(三)——一个简单的maven项目

    目标: 对构建生命周期 (build  lifecycle),Maven仓库 (repositories),依赖管理 (dependency management)和项目对象模型 (Project O ...

随机推荐

  1. 2.6 EmpController

    package com.hy.controller; import javax.servlet.http.HttpServletRequest; import javax.servlet.http.H ...

  2. 【剑指Offer】【树】从上到下打印二叉树(层序遍历)

    题目:从上往下打印出二叉树的每个节点,同层节点从左至右打印. A:创建一个辅助队列,将根节点入队,添加到输出的vector中 循环:到队为空为止 若二叉树有左结点则将左节点入队 若二叉树有右节点则将右 ...

  3. PCIe卡设计资料保存:536-基于ZU7EV的FMC 通用PCIe卡

    基于ZU7EV的FMC 通用PCIe卡   一.板卡简介 基于3U PXIe的ZU11EG/ZU7EG/ZU7EV的通用 ,实现FMC的数据接口和主控计算,广泛应用于工业控制,检测,视觉处理.支持工业 ...

  4. 泛微js附件必填

    function fieldViewAttr(fieldid, viewtype) { alert('11') jQuery("#field" + fieldid).attr(&q ...

  5. Server2008通过bat命令自动定时备份MySQL数据库

    第一种方法: 环境: MySQL 安装位置:D:\MySQL 论坛数据库名称为:Db_Test 数据库备份目的地:D:\db_bak\ 1.首先新建一个bat文件 rem ************** ...

  6. 【SQL Server】中的日期函数和日期数据类型

    SQL Server Date 函数 SQL Server的重要日期函数包括: 函数 描述 参数含义 GETDATE() 返回当前的日期和时间   DATEPART(datepart,date)  返 ...

  7. linux中安装doker

    1.更新yum为最新的 yum -y update 2.卸载旧版的docker sudo yum remove -y docker* 3.安装需要的软件包 yum install -y yum-uti ...

  8. 去除Bam文件中的PCR 重复

    1.使用samtools 去除重复 samtools sort -n -@ 20 file.bam |samtools fixmate -m -@20 - - |samtools sort -@ 20 ...

  9. pure-ftpd

    1.安装服务 yum install epel-release yum -y install pure-ftpd 2.启动服务如果报错,看一下是否是缺库文件导致. locate libpq.so.5 ...

  10. python经典例题

    [程序1] 题目:有1.2.3.4个数字,能组成多少个互不相同且无重复数字的三位数?都是多少? num_list=[] cou=0 for i in range(1,5): for j in rang ...