Learn / Rust / Option, Result and match: no surprises

Rust, lesson 5 of 5

Option, Result and match: no surprises

Many languages have a "null" value that crashes programs when nobody expects it. Rust has no null. A value that might be missing is an Option: either Some(value) or None. match handles each case:

fn find_port(service: &str) -> Option<u16> {
    match service {
        "ssh" => Some(22),
        "https" => Some(443),
        _ => None,
    }
}

fn main() {
    match find_port("ssh") {
        Some(p) => println!("Port {}", p),
        None => println!("Unknown service"),
    }
}

The _ means "anything else". A match must cover every case. Forget one and Rust refuses to build:

fn main() {
    let port: Option<u16> = None;
    match port {
        Some(p) => println!("{}", p),
    }
}

Rust refuses to build this.

For things that can fail, such as turning text into a number, Rust gives back a Result: Ok(value) or Err(problem). You cannot use the value without deciding what to do about the error:

fn main() {
    let input = "8o80";
    match input.parse::<u16>() {
        Ok(n) => println!("Port {}", n),
        Err(_) => println!("Not a valid port: {}", input),
    }
}

Check yourself

1. What does Rust use instead of null?

2. What happens if a match forgets the None case?

3. With find_port from this lesson, what does matching find_port("ftp") print?

4. What do you get back from something that can fail, such as reading a number from text?