if let
if let
allows you to combine if and let together to reduce the overhead of certain kinds of pattern matches.數據結構
let option = Some(12); if let Some(x) = option { foo(x); } else { bar(); }
while let
In a similar fashion, while let can be used when you want to conditionally loop as long as a value matches a certain pattern.oop
let mut v = vec![1, 3, 5, 7, 11]; while let Some(x) = v.pop() { println!("{}", x); }
使用|
來匹配複合模式:code
let x = 1; match x { 1 | 2 => println!("one or two"), 3 => println!("three"), _ => println!("anything"), } //打印結果: one or two
若是有一個複雜的數據類型,例如: struct,咱們能夠使用pattern來解構:three
struct Point { x: i32, y: i32, } let origin = Point { x: 0, y: 0 }; match origin { Point { x, y } => println!("({},{})", x, y), }
咱們使用:
來指定不一樣的名字:ip
struct Point { x: i32, y: i32, } let origin = Point { x: 0, y: 0 }; match origin { Point { x: x1, y: y1 } => println!("({},{})", x1, y1), }
若是咱們只關係其中的某些值,咱們沒必要指定全部的名字:element
struct Point { x: i32, y: i32, } let origin = Point { x: 0, y: 0 }; match origin { Point { x, .. } => println!("x is {}", x), }
打印出 x is 0
get
解構
也徹底適用於tuple
和enums
string
match some_value { Ok(value) => println!("got a value: {}", value), Err(_) => println!("an error occurred"), } fn coordinate() -> (i32, i32, i32) { // generate and return some sort of triple tuple } let (x, _, z) = coordinate();
類似的,咱們能夠使用..
來忽略多個值:it
enum OptionalTuple { Value(i32, i32, i32), Missing, } let x = OptionalTuple::Value(5, -2, 3); match x { OptionalTuple::Value(..) => println!("Got a tuple!"), OptionalTuple::Missing => println!("No such luck."), }
若是須要獲取一個引用,咱們能夠使用ref
關鍵字:io
let x = 5; match x { ref r => println!("Got a reference to {}", r), }
這裏,r
在match
中的數據類型爲&i32
,換句話說,ref
在使用patterns中建立了一個引用。若是須要一個可變引用,能夠使用ref mut
let mut x = 5; match x { ref mut mr => println!("Got a mutable reference to {}", mr), }
咱們使用...
來匹配一個範圍的值:
let x = 1; match x { 1 ... 5 => println!("one through five"), _ => println!("anything"), }
咱們能夠經過@
綁定值到一個命名變量上:
let x = 1; match x { e @ 1 ... 5 => println!("got a range element {}", e), _ => println!("anything"), }
在匹配複雜的數據結構中是很是有用的,例如:
#[derive(Debug)] struct Person { name: Option<String>, } let name = "Steve".to_string(); let mut x: Option<Person> = Some(Person { name: Some(name) }); match x { Some(Person { name: ref a @ Some(_), .. }) => println!("{:?}", a), _ => {} }
使用@
和|
,能夠分別匹配不一樣的部分:
let x = 5; match x { e @ 1 ... 5 | e @ 8 ... 10 => println!("got a range element {}", e), _ => println!("anything"), }
enum OptionalInt { Value(i32), Missing, } let x = OptionalInt::Value(5); match x { OptionalInt::Value(i) if i > 5 => println!("Got an int bigger than five!"), OptionalInt::Value(..) => println!("Got an int!"), OptionalInt::Missing => println!("No such luck."), }