我们已经看过多次if表达式。总的来说,花括号是强制性的,if表达式能够有可选的else从句,而且多个if/else结构能够被链接在一起:
if false { println!("that‘s odd"); } else if true { println!("right"); } else { println!("neither true nor false"); }if结构的条件必须是bool类型的(没有隐式转换发生)。如果分支是有值的代码块,那么所有的代码分支所能够执行到的最后表达式的值必须拥有相同的类型:
fn signum(x: int) -> int { if x < 0 { -1 } else if x > 0 { 1 } else { 0 } }
Rust的match结构式C中switch结构的通用、简洁版本。你提供一个值和一些分支,每个分支用一个模式标识,然后代码按顺序将值与每一个模式比较,直到其中一个匹配为止。模式匹配成功后执行相应的分支:
match my_number { 0 => println!("zero"), 1 | 2 => println!("one or two"), 3..10 => println!("three to ten"), _ => println!("something else") }
不像C,分支没有“falling through”一说,仅仅一个分支被执行。当执行完成时,没有显式的break跳出结构。
一个match的分支包含一个模式和箭头=>,随后是一个动作(表达式)。字面值是有效的模式,且仅仅匹配它自己的值。只要每个变量绑定了相同的变量集,单个的分支可能通过管道操作符(|)结合来匹配多个模式。数字字面值的范围模式可用两点来表示,就像M..N。下划线(_)是一个通配符,能够匹配任意单个值。(..)是一个不同的通配符,能够匹配枚举变量的一个或多个域。
模式匹配成功的分支,跟随在胖箭头=>后的表达式将被估值。每个分支以逗号分隔。在分支中使用块表达式是方便的,这种情况下,逗号是可选的。
match my_number { 0 => { println!("zero") } _ => { println!("something else") } }
match结构必须是无遗漏的:对于每种可能的情况都必须有分支覆盖。举个例子,如果先前例子中通配符模式的分支被忽略,类型检查器将会拒绝它。
模式匹配更强大的应用是解构:为绑定名字到数据类型的内容而匹配。
注意:下面的代码使用元组((f64,f64))将在5.3节解释。现在你将元组视为列表项。
use std::f64; use std::num::atan; fn angle(vector: (f64, f64)) -> f64 { let pi = f64::consts::PI; match vector { (0.0, y) if y < 0.0 => 1.5 * pi, (0.0, _) => 0.5 * pi, (x, y) => atan(y / x) } }
一个变量名匹配任意值,且在分支动作的作用域中将该变量名绑定到所匹配值的值上。因此,(0.0, y)匹配任何第一个元素是0的元组,且绑定y到第二个元素。(x, y)匹配任何二元元组,且绑定两个元素给变量。(0.0, _)匹配任何第一个元素是0的元组,且不绑定任何值给第二个元素。
通过使用variable@ pattern,一个子模式也能够限制变量。例如:match age { a @ 0..20 => println!("{} years old", a), _ => println!("older than 21") }
任何match的分支可以有一个判断从句(写做if EXPR),叫做模式断言,它是bool类型的表达式,在模式匹配后,对是否选择该分支做出判断。断言表达式也在以模式绑定的变量的作用域内。angle例子中的第一个分支显示了模式断言的例子。
你已经看到了简单的let绑定,但let比你被引导所相信的更具想象力,它也支持解构模式。举个例子,你能够通过一次引入两个变量:a和b,来提取元组中的多个域。
let (a, b) = get_tuple_of_two_ints();
let绑定仅仅工作在不可拒绝的模式下:即模式不能出现匹配失败的情况。这不包括let匹配字面值和大多数enum变量
let mut cake_amount = 8; while cake_amount > 0 { cake_amount -= 1; }loop表示无限循环,它是比写while true更好地方式。
let mut x = 5u; loop { x += x - 3; if x % 5 == 0 { break; } println!("{}", x); }
这段代码打印怪异的数字序列,当它发现某个数能被5整除时终止循环。
也有能被用于遍历数的范围的for循环。
for n in range(0, 5) { println!("{}", n); }
上述片段打印从0到5的整数值。
更一般的,for循环能够在任何实现Iterator特性的数据结构中工作。数据结构能够提供一个或多个方法返回它们内容中的迭代器。举个例子,字符串支持通过多种方式迭代其内容。
let s = "Hello"; for c in s.chars() { println!("{}", c); }上述片段垂直地打印“Hello”中的字符,每个字符后添加新的换行。
原文:http://blog.csdn.net/wsgzg1991/article/details/22980411