当前位置: 首页 > java >正文

关于rust的所有权以及借用borrowing

如何从内存中申请空间来存放程序的运行内容,如何在不需要的时候释放这些空间,以下的几种方式:

  1. 垃圾回收机制(GC),在程序运行时不断寻找不再使用的内存,典型代表:Java、Go。
  2. 手动管理内存的分配和释放, 在程序中,通过函数调用的方式来申请和释放内存,典型代表:C++。
  3. 通过所有权来管理内存,编译器在编译时会根据一系列规则进行检查。

其中 Rust 选择了第三种,最妙的是,这种检查只发生在编译期,因此对于程序运行期,不会有任何性能上的损失。Ownership和Borrowing也是rust特有的机制,Rust 用所有权避免内存泄漏和悬垂指针,不用垃圾回收。

以下尝试用最简单的方式来解释这2种机制。

✅ 一、所有权(Ownership)——“一个东西只能有一个人管”
规则:每个值有且仅有一个“主人”(变量),主人离开作用域,值就被销毁。赋值或传参时,所有权被转移(不是复制!)。

let s1 = String::from("hello");
let s2 = s1;        // s1 把所有权给了 s2
println!("{}", s1); // ❌ 错误!s1 已经“失效”

总结:s1 被“move”了,不能再用。

✅ 二、借用(Borrowing)——“用一下,不拿走”
想用值但不拿走所有权?用引用(&)。

let s1 = String::from("hello");
let len = calc_length(&s1);  // 借用 s1
println!("{}", s1);               // ✅ OK!s1 还在fn calc_length(s: &String) -> usize {s.len()  // 只是“读”,不拥有
}

总结: 🔑 &s1 是“借用”——你用,但不归你。

✅ 三、可变借用——“借走还能改”
默认借用是只读的。要修改,必须可变借用。

let mut s = String::from("hello");
change(&mut s);           // 可变借用,注意:当使用 mut 关键字声明一个变量时,该变量就可以被修改
println!("{}", s);        // 输出 "hello world"fn change(s: &mut String) {s.push_str(" world");	//追加
}

⚠️ 注意:同一时间,只能有一个可变借用,或多个不可变借用(不能又读又写)。
这种限制的好处就是使 Rust 在编译期就避免数据竞争,数据竞争可由以下行为造成:

  1. 两个或更多的指针同时访问同一数据
  2. 至少有一个指针被用来写入数据
  3. 没有同步数据访问的机制
fn main() {let mut s = String::from("hello");let r1 = &s;      // ✅ 不可变借用let r2 = &s;      // ✅ 还可以再借一个(读-读允许)let r3 = &mut s;  // ❌ 错误!不能在 r1、r2 存在时借可变引用println!("{}, {}, and {}", r1, r2, r3);
}let mut s = String::from("hello");
let r1 = &mut s;        // ✅ 可变借用
let r2 = &s;            // 不行!只要有 &mut s,就不能再有 &s。//很多时候,大括号可以帮我们解决一些编译不通过的问题,通过手动限制变量的作用域:
let mut s = String::from("hello");
{let r1 = &mut s;
} // r1 在这里离开了作用域,所以我们完全可以创建一个新的引用
let r2 = &mut s;

✅ 总结
所有权:值只有一个主人,主人走了,值就没了。
引用:&x 借来用,不拿走。
可变引用:&mut x 借来还能改,但只能一个。

http://www.xdnf.cn/news/20233.html

相关文章:

  • 汽车 信息娱乐系统 概览
  • 【前端教程】JavaScript 实现图片鼠标悬停切换效果与==和=的区别
  • 寻找AI——初识3D建模AI
  • 中囯移动电视盒子(魔百和)B860AV2.1-A2和CM311-5-zg刷机手记
  • MacOS 通过Homebrew 安装nvm
  • 深度学习中的Zero-shot(零次学习)
  • 【Python基础】 18 Rust 与 Python print 函数完整对比笔记
  • 通过Gen AI SDK调用gemini 2.5 pro,单独上传pdf文件 | ai agent 开发笔记 2025.9.2 Day 2
  • 确保 SQL Server 备份安全有效的最佳实践
  • 【面试场景题】spring应用启动时出现内存溢出怎么排查
  • Nginx 高性能调优指南:从配置到原理
  • 用 Cursor AI 快速开发你的第一个编程小程序
  • Sentinel和Cluster,到底该怎么选?
  • 2025高教社数学建模国赛A题 - 烟幕干扰弹的投放策略(完整参考论文)
  • 【Tailwind, Daisyui】响应式表格 responsive table
  • 一文教您学会Ubuntu安装Pycharm
  • 管家婆分销ERP A/V系列导出提示加载数据过大的处理方式
  • 【Python基础】 17 Rust 与 Python 运算符对比学习笔记
  • k8s除了主server服务器可正常使用kubectl命令,其他节点不能使用原因,以及如何在其他k8s节点正常使用kubectl命令??
  • 人工智能机器学习——聚类
  • 2025 汽车租赁大会:九识智能以“租赁+运力”革新城市智能配送
  • 指定端口-SSH连接的目标(告别 22 端口暴力破解)
  • 结构体简介
  • window cmd 命令行中指定代理
  • 对于单链表相关经典算法题:203. 移除链表元素的解析
  • 数据结构:栈和队列力扣算法题
  • 空域属不属于自然资源?(GPT5)
  • Redis-事务与管道
  • 使用CI/CD部署后端项目(gin)
  • 因泰立科技:用激光雷达重塑智能工厂物流生态