Rust by Example - страница 19
>
• iter_mut - This mutably borrows each element of the collection, allowing for the collection to be modified in place.
>fn main() {
>let mut names = vec!["Bob", "Frank", "Ferris"];
>for name in names.iter_mut() {
>*name = match name {
>&mut "Ferris" => "There is a rustacean among us!",
>_ => "Hello",
>}
>}
>println!("names: {:?}", names);
>}
>הההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההה
>XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX
In the above snippets note the type of match branch, that is the key difference in the types of iteration. The difference in type then of course implies differing actions that are able to be performed.
Rust provides pattern matching via the match keyword, which can be used like a C switch. The first matching arm is evaluated and all possible values must be covered.
>fn main() {
>let number = 13;
>// TODO ^ Try different values for `number`
>println!("Tell me about {}", number);
>match number {
>// Match a single value
>1 => println!("One!"),
>// Match several values
>2 | 3 | 5 | 7 | 11 => println!("This is a prime"),
>// TODO ^ Try adding 13 to the list of prime values
>// Match an inclusive range
>13..=19 => println!("A teen"),
>// Handle the rest of cases
>_ => println!("Ain't special"),
>// TODO ^ Try commenting out this catch-all arm
>}
>let boolean = true;
>// Match is an expression too
>let binary = match boolean {
>// The arms of a match must cover all the possible values
>false => 0,
>true => 1,
>// TODO ^ Try commenting out one of these arms
>};
>println!("{} -> {}", boolean, binary);
>}
>הההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההה
>XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX
A match block can destructure items in a variety of ways.
Tuples can be destructured in a match as follows:
>fn main() {
>let triple = (0, -2, 3);
>// TODO ^ Try different values for `triple`
>println!("Tell me about {:?}", triple);
>// Match can be used to destructure a tuple
>match triple {
>// Destructure the second and third elements
>(0, y, z) => println!("First is `0`, `y` is {:?}, and `z` is {:?}", y, z),
>(1, ..) => println!("First is `1` and the rest doesn't matter"),
>// `..` can be the used ignore the rest of the tuple
>_ => println!("It doesn't matter what they are"),
>// `_` means don't bind the value to a variable
>}
>}
>הההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההה
>XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX
An enum is destructured similarly:
>// `allow` required to silence warnings because only
>// one variant is used.
>#[allow(dead_code)]
>enum Color {
>// These 3 are specified solely by their name.
>Red,
>Blue,
>Green,
>// These likewise tie `u32` tuples to different names: color models.
>RGB(u32, u32, u32),
>HSV(u32, u32, u32),