主要有两个问题:

  1. let x = y如何翻译成伪英语/伪代码?
  2. if let x = y {}块是如何一步一步地工作的?

总是假设let声明了一个变量,直到我遇到了if let(下面的代码),然后go 谷歌搜索.

let config_max = Some(3u8);
if let Some(max) = config_max {
    println!("The maximum is configured to be {}", max);
} else {
    println!("xyz");
}

StackOverflow线程解释了这一点.所以我把它理解为让它只判断模式和值是否匹配,而不是自己声明变量:

let y = Some(5);
if let Some(x) = y { doZ(x); }
// 1. let Some(x) = y -- see if pattern Some(x) matches value y, if yes execute next expression
// 2. Some(x) = y -- the next expression, assign value of y to "variable Some(x)"
// if ( 1 and 2 are successful) { execute this }

但是,如果let只用于模式值匹配/求值,那么为什么在变量声明中使用它呢? 答:因为它不仅用于模式匹配,而且是变量声明所需要的.

let y = Some(5);
if let Some(x) = y { doZ(x); }
// if -- if
// let Some(x) = y -- ( if pattern Some(x) matches Some(5), declare variable Some(x) and assign value Some(5) to it ) 
// doZ(x) -- { execute doZ function and pass x as an argument}

上述"翻译"是否意味着let Some(x) = Some(5)==let x = 5?如果是,这是如何发生的?B-Option<T>Enum类型的全部要点不是要与原始T不同吗?

if let x = 5 { doZ(x); } // a
// Warning: x = 5 is irrefutable, consider using just "let" without "if".

5 == Some(5) // b, false

上面的错误还反驳了if let Some(x) = y中的if是否是常规的if,查找布尔值,然后它将运行"{}"中的代码.但是let是一个语句,它不会返回bool或其他任何值,不管有没有if.那么,这是否意味着在这个特定的例子中,if实际上不是if(执行代码需要bool),而是一个令人精疲力竭的match?如果是,为什么是if,而不是其他/新的关键字?

推荐答案

  1. let本身只是变量赋值(如果模式是无可辩驳的,则可能使用模式匹配).
  2. if本身是基于布尔值的分支
  3. if let不仅仅是letif的奇怪混搭,而是一个单独的 struct :

if let能做什么?它try 将一个值与一个模式进行匹配,并在这样做的过程中将该值的一部分绑定到正在匹配的模式.只有当模式实际匹配成功时,它才会执行if let块中的代码:

let x = 5; // simple variable assignment

let (x, y) = (3, 4); // assignment with pattern matching

if x % 2 == 0 { // only do this code if number is even
  println!("x is even");
}

// if let to do pattern-matching and assignment, 
// but where the pattern might potentially not match
if let Some(x) = function_that_returns_option() {
  println!("The function returned Some(x) with x = {}", x);
}

// if the function had returned None instead, then nothing would have been printed and nothing would have been assigned to that x.

Rust相关问答推荐

Rust kill std::processs::child

创建包含缺失值的框架

在自身功能上实现类似移动的行为,以允许通过大小的所有者进行呼叫(&;mut;self)?

MutexGuard中的过滤载体不需要克隆

如果LET;使用布尔表达式链接(&Q);

Box::new()会从一个堆栈复制到另一个堆吗?

什么时候和为什么S最好是按值或引用传递简单类型

S在Cargo.toml中添加工作空间开发依赖关系的正确方法是什么?

类型批注需要静态生存期

如何在Rust中将选项<;选项<;字符串>;转换为选项<;选项&;str>;?

为什么基于高山Linux的Docker镜像不能在绝对路径下找到要执行的命令?

Rust编译器似乎被结果类型与anyhow混淆

`actix-web` 使用提供的 `tokio` 运行时有何用途?

当我编译 Rust 代码时,我是否缺少 AVX512 的目标功能?

提取指向特征函数的原始指针

Rust LinkedList 中的borrow 判断器错误的原因是什么?

在没有任何同步的情况下以非原子方式更新由宽松原子操作 Select 的值是否安全?

decltype、dyn、impl traits,重构时如何声明函数的返回类型

使用 Rust 从 Raspberry Pi Pico 上的 SPI 读取值

&self 参数在 trait 的功能中是必需的吗?