
18.2 可辩驳性模式是否会无法匹配18.2.1. 模式的两种形式模式有两种形式- 可辩驳的refutable意味着它们可能匹配失败- 无可辩驳的irrefutable意味着它们不会失败你可以把它理解为无论怎么写都会成功的模式能够匹配任意可能传入值的模式就是无可辩驳的。例如let x 5;这个语句不可能失败因为x能匹配表达式右侧所有可能的值。无法匹配某些可能值的模式就是可辩驳的。例如if let Some(x) a_value如果右侧的值是None模式就会匹配失败。函数参数、let语句和for循环只接受无可辩驳模式。例如let a: Optioni32 Some(5); let Some(x) a;Some(x) a是可辩驳的因为也有可能是None但let语句只接受无可辩驳模式所以编译器会报错。那该怎么改呢可以使用if let也可以使用let...else来处理匹配失败的情况let a: Optioni32 Some(5); if let Some(x) a { // ... }let a: Optioni32 Some(5); let Some(x) a else { return; };if let、while let和let...else同时支持可辩驳和无可辩驳模式。实际上如果你在if let、while let或let...else中使用无可辩驳模式编译器会发出警告因为从概念上讲这里本来就存在失败的可能。例如if let x 5 { println!({x}); };输出$ cargo run Compiling patterns v0.1.0 (/tmp/ch18-refresh/patterns) warning: irrefutable if let pattern -- src/main.rs:2:8 | 2 | if let x 5 { | ^^^^^^^^^ | note: this pattern will always match, so the if let is useless help: consider replacing the if let with a let note: #[warn(irrefutable_let_patterns)] on by default warning: patterns (bin patterns) generated 1 warning Finished dev profile [unoptimized debuginfo] target(s) in 0.09s Running target/debug/patterns 5编译器会警告 “irrefutableif letpattern”。那是因为在本应用于可辩驳模式的上下文中使用无可辩驳模式是没有意义的。基于这些概念再想想match表达式的分支除了最后一个分支以外其他分支都应该是可辩驳的而最后一个分支应该是无可辩驳的因为它需要匹配所有剩余情况。