语言学习
1.命名空间
Rust 用 模块(mod) 和 use 实现命名空间,避免命名冲突
rust
// 定义一个命名空间(模块)
mod my_module {
// 模块内的函数,需要 pub 才能外部访问
pub fn hello() {
println!("你好,来自 my_module!");
}
// 子命名空间
pub mod sub_module {
pub fn add(a: i32, b: i32) -> i32 {
a + b
}
}
}
// 引入命名空间(相当于 using namespace)
use my_module::sub_module;
fn main() {
my_module::hello(); // 直接调用模块函数
println!("1+2={}", sub_module::add(1, 2)); // 调用子模块
}2.变量声明 + 赋值
Rust 变量默认不可变,这是 Rust 最大的特点之一
rust
fn main() {
// 1. 不可变变量(默认),不能二次赋值
let a = 10;
println!("不可变变量 a = {}", a);
// 2. 可变变量(必须加 mut)
let mut b = 20;
b = 30; // 允许修改
println!("可变变量 b = {}", b);
// 3. 常量(必须指定类型,编译期确定值)
const PI: f64 = 3.14159;
println!("常量 PI = {}", PI);
// 4. 类型注解(手动指定类型)
let c: i32 = 100;
let name: &str = "Rust";
// 5. 变量遮蔽(同名覆盖,允许修改变量类型)
let x = 5;
let x = x + 1; // 合法,创建新变量
let x = "hello"; // 甚至可以改类型!
println!("遮蔽后的 x = {}", x);
}3.条件判断(if /else if /else)
Rust 没有三元运算符,但 if 可以当表达式使用(直接赋值)。Rust 中 if 是表达式,不是语句!意味着:if 可以直接返回值,赋值给变量。
rust
let age = 20;
// 基础条件判断
if age >= 18 {
println!("成年");
} else if age >= 12 {
println!("青少年");
} else {
println!("儿童");
}
// if 作为表达式(直接赋值)
let status = if age >= 18 { "成年" } else { "未成年" };
println!("状态:{}", status);
//if let(只关心成功)
if let Ok(value) = check_positive(20) {
println!("成功:{}", value);
}
// 条件必须是 bool 类型,Rust 不允许数字当条件!
// if 1 { ... } 报错!4.循环结构(loop /while/for)
Rust 有 3 种循环,功能完全覆盖所有场景。
无限循环 loop
rust
loop {
i += 1;
if i == 3 {
println!("继续");
continue; // 跳过本次
}
if i == 5 {
println!("退出循环");
break; // 退出循环
}
println!("loop: {}", i);
}条件循环 while
rust
let mut i = 0;
while i < 3 {
println!("while: {}", i);
i += 1;
}遍历循环 for(最常用)
rust
// 遍历范围 1~4
for i in 1..5 {
println!("for 范围: {}", i);
}
// 遍历数组
let arr = ["苹果", "香蕉", "橙子"];
for fruit in arr {
println!("水果: {}", fruit);
}特殊语法
①模式匹配 match(超级强大)
相当于 switch
rust
let num = 2;
match num {
1 => println!("一"),
2 => println!("二"),
3 | 4 => println!("三或四"),
_ => println!("其他"), // 必须覆盖所有情况
}
// 同时处理成功 + 失败:match(最完整)
match check_positive(30) {
Ok(v) => println!("成功:{}", v),
Err(e) => println!("错误:{}", e),
}② 元组(Tuple)
可以存不同类型的数据,固定长度。
rust
// 定义元组
let person = ("张三", 18, true);
// 解构赋值
let (name, age, is_student) = person;
println!("{},{}岁,学生:{}", name, age, is_student);③ 所有权 & 引用(Rust 核心)
let s1 = String::from("hello");
let s2 = &s1; // 引用(借用),不转移所有权
println!("s1: {}, s2: {}", s1, s2); // 都能用!④ 函数返回值
Rust 函数最后一行不加 ; 就是返回值,不用写 return。
fn add(a: i32, b: i32) -> i32 {
a + b // 无分号 = 返回值
}
fn main() {
println!("3+5={}", add(3,5));
}成功 / 失败结果封装:Result<T, E>
这是 Rust 官方标准的成功 / 失败封装,所有项目必用!
rust
// 定义一个函数:成功返回数字,失败返回字符串
fn check_positive(n: i32) -> Result<i32, String> {
if n > 0 {
Ok(n) // 成功:用 Ok() 包裹
} else {
Err("数字必须大于 0".to_string()) // 失败:用 Err() 包裹
}
}
fn main() {
let result = check_positive(10);
// 使用 match 处理成功/失败
match result {
Ok(value) => println!("成功:{}", value),
Err(err) => println!("失败:{}", err),
};
}成功 / 失败(Result)、空值(Option)
Cargo.toml文件
1. 先记住:Rust 统一的成功 / 失败封装
rust
运行
Result<T, E>
Ok(T) 成功
Err(E) 失败
Option<T>
Some(T) 有值
None 空值所有错误处理都是围绕这两个枚举。
2. unwrap () —— 最简单但最粗暴
成功就返回值,失败直接崩溃(panic)
适合:测试、示例、你确定一定不会失败的情况。
rust
运行
let r: Result<i32, String> = Ok(100);
let v = r.unwrap(); // 100
let e: Result<i32, String> = Err("错了".into());
e.unwrap(); // 程序直接崩溃3. expect ("提示") —— 比 unwrap 好,带错误信息
崩溃时会打印你写的提示信息,生产代码推荐用这个代替 unwrap。
rust
运行
let r: Result<i32, String> = Err("读取文件失败".into());
r.expect("读取配置文件时出错");崩溃信息会显示:
plaintext
读取配置文件时出错: 读取文件失败4. ? 运算符 —— Rust 最优雅、最常用
遇到错误直接返回错误,不崩溃!
只能用在返回 Result / Option 的函数里。
rust
运行
fn foo() -> Result<i32, String> {
let num = bar()?; // 如果 bar() 返回 Err,直接返回给调用者
Ok(num)
}
fn bar() -> Result<i32, String> {
Ok(10)
}一句话:
? = 自动 match + 自动返回错误
5. 完整实战示例(最常用写法)
你复制就能跑,这就是真实 Rust 项目写法:
rust
运行
// 可能成功/失败的函数
fn divide(a: i32, b: i32) -> Result<i32, String> {
if b == 0 {
return Err("除零错误".to_string());
}
Ok(a / b)
}
// 使用 ? 自动传播错误
fn calc() -> Result<i32, String> {
let a = divide(10, 2)?;
let b = divide(20, 5)?;
Ok(a + b)
}
fn main() {
// 1. expect 用法
divide(10, 2).expect("计算失败");
// 2. match 完整处理
match calc() {
Ok(v) => println!("结果: {}", v),
Err(e) => println!("错误: {}", e),
}
// 3. if let 只处理成功
if let Ok(v) = divide(10, 2) {
println!("成功: {}", v);
}
}6. 快速选择指南(背这个就够)
表格
| 语法 | 用途 | 推荐场景 |
|---|---|---|
unwrap() | 成功返回,失败崩溃 | 测试、示例 |
expect(msg) | 成功返回,崩溃带提示 | 小工具、脚本、确定不会错 |
? | 自动返回错误 | 90% 项目代码首选 |
match | 完整处理成功 / 失败 | 必须处理错误时 |
if let | 只关心成功 | 简单逻辑 |
7. 终极一句话总结
- unwrap/expect:简单但会崩溃
- ?:优雅不崩溃,项目必备
- Result + ? 是 Rust 错误处理的标准组合
错误处理三神器(必背)
rust
运行
val.unwrap(); // 成功返回,失败崩溃
val.expect("信息"); // 失败带提示
val?; // 自动返回错误(项目首选)8. 结构体 Struct
rust
运行
struct User { name: String }
let u = User { name: "张三".into() };9. 向量 Vec(动态数组)
rust
运行
let mut v = vec![1,2,3];
v.push(4);10. 字符串 String
rust
运行
let s = String::from("hello");
let s2 = &s; // 引用(不转移所有权)