Rust 编程之道

Rust 语言圣经中文版(rust-book-zh-cn-shieber.pdf) 来源:/books/rust-book-zh-cn-shieber.pdf 页数:300页(扫描版PDF,文本提取为空) 译者:Shieber(基于 Steve Klabnik 和 Carol Nichols 的英文版)

核心概念

1. 所有权系统(Ownership)

Rust 的核心创新,解决了内存安全问题而不需要垃圾回收:

  • 所有权规则:

    • Rust 中的每个值都有一个所有者(owner)
    • 当所有者离开作用域时,值会被自动释放
    • 同一时刻只能有一个可变引用,或多个不可变引用
  • 借用(Borrowing):

    • &T 不可变引用
    • &mut T 可变引用
    • 借用规则:不能同时拥有可变引用和不可变引用
fn main() {
    let s1 = String::from("hello");
    let s2 = s1; // s1 被移动到 s2
    // println!("{}", s1); // 错误:s1 已失效
    println!("{}", s2); // 正确
}

2. 生命周期(Lifetime)

  • 引用必须有效的代码区域
  • 生命周期注解:'a, 'b 等
  • 编译器自动推断生命周期
fn longest<'a>(x: &'a str, y: &'a str) -> &'a str {
    if x.len() > y.len() { x } else { y }
}

3. 所有权系统的高级抽象

  • Box:堆分配指针
  • Rc:引用计数(多所有者)
  • RefCell:内部可变性
  • Arc:原子引用计数(线程安全)

核心特性

模式匹配(Pattern Matching)

match value {
    Some(x) => println!("Got: {}", x),
    None => println!("Nothing"),
}

错误处理

  • Result<T, E>:可恢复错误
  • panic!:不可恢复错误
  • ? 运算符传播错误
fn read_file() -> Result<String, io::Error> {
    let mut file = File::open("foo.txt")?;
    let mut contents = String::new();
    file.read_to_string(&mut contents)?;
    Ok(contents)
}

trait(特性)

类似于其他语言的接口:

trait Summary {
    fn summarize(&self) -> String;
}
 
struct Article {
    title: String,
    content: String,
}
 
impl Summary for Article {
    fn summarize(&self) -> String {
        format!("{}: {}", self.title, &self.content[..50])
    }
}

泛型

fn largest<T: PartialOrd>(list: &[T]) -> &T {
    let mut largest = &list[0];
    for item in list {
        if item > largest {
            largest = item;
        }
    }
    largest
}

闭包

let add = |a, b| a + b;
let result = add(2, 3);

迭代器

let v = vec![1, 2, 3];
let sum: i32 = v.iter().map(|x| x * 2).sum();

内存安全保证

Rust 通过以下机制保证内存安全:

  1. 借用检查器:编译时检查引用有效性
  2. 生命周期:确保引用不会 outlive 其数据
  3. 类型安全:防止无效类型转换
  4. 穷尽匹配:编译器确保所有情况都被处理

并发编程

  • 线程:std::thread
  • 消息传递:std::sync::mpsc
  • 共享状态:Mutex<T>, Arc<T>
  • Send + Sync: trait 标记线程安全
use std::thread;
use std::sync::mpsc;
 
let (tx, rx) = mpsc::channel();
 
thread::spawn(move || {
    tx.send("Hello from thread").unwrap();
});
 
println!("{}", rx.recv().unwrap());

Cargo 包管理

# 创建新项目
cargo new project_name
 
# 构建项目
cargo build
 
# 运行项目
cargo run
 
# 测试
cargo test
 
# 发布
cargo build --release

Cargo.toml

[package]
name = "package_name"
version = "0.1.0"
edition = "2021"
 
[dependencies]
serde = "1.0"
tokio = { version = "1", features = ["full"] }
 
[dev-dependencies]
criterion = "0.5"

智能指针深度解析

指针特性适用场景
Box<T>堆分配,大小已知递归类型、大结构体
Rc<T>引用计数单线程多所有者
Arc<T>原子引用计数多线程多所有者
RefCell<T>内部可变性运行时借用检查
Rc<RefCell<T>>组合使用多个所有者需要修改

高级主题

unsafe Rust

绕过借用检查器的能力:

unsafe {
    // 直接操作原始指针
    // 调用外部函数
    // 修改静态变量
}

宏系统

  • 声明宏:macro_rules!
  • 过程宏:derive, attribute-like, function-like

零成本抽象

Rust 抽象不引入运行时开销:

  • 迭代器内联
  • 泛型单态化
  • 静态分派

学习路径建议

  1. 基础:所有权、借用、生命周期
  2. 进阶:trait、泛型、错误处理
  3. 实战:并发、异步、宏
  4. 深入:unsafe Rust、编译器内部

相关笔记