thanasis2028
thanasis2028

Reputation: 125

Combining multi-pattern with conditionals in match

I'm trying to check if a variable b of a type Option<A> is equal to a of the same type A or None. It would seem idiomatic to use a match statement with multi pattern Some(a) | None, but I can't find a way to make it work.

Is there a way to express this pattern using match or should I just use a normal if pattern?

Example (also in https://play.rust-lang.org/?version=stable&mode=debug&edition=2021&gist=217b4559a73d59409f1d6afe7365d57c):

fn main() {
    let a = 3;
    let b = Some(5);
    
    // Works but has code duplication
    match b {
        Some(b_val) if b_val == a => {
            println!("do something");
        }
        None => {
            println!("do something");
        }
        Some(_) => {
            println!("do something else");
        }
    }
    
    // Works but not very idiomatic
    if b.is_none() || b.unwrap() == a {
        println!("do something");
    } else {
        println!("do something else");
    }
    
    // Does not work
    match b {
        Some(b_val) if b_val == a | None => {
            println!("do something");
        }
        Some(_) => {
            println!("do something else");
        }
    }
}

Upvotes: 1

Views: 92

Answers (2)

Denys S&#233;guret
Denys S&#233;guret

Reputation: 382150

You can check inequality instead of equality:

match b {
    Some(b_val) if b_val != a => {
        println!("do something else");
    }
    _ => {
        println!("do something");
    }
}

Upvotes: 1

rustyhu
rustyhu

Reputation: 2147

I can only come up with a const a:

fn main() {
    const a: i32 = 3;
    let b = Some(5);
    
    match b {
        Some(a) | None  => {
            println!("do something");
        }
        _ => {
            println!("do something else");
        }
    }
}

Or use if:

fn main() {
    let a = 3;
    let b = Some(5);
    
    if b == None || b == Some(a) {
        println!("do something");
    } else {
        println!("do something else");
    }
}

Output:

do something else

Upvotes: 1

Related Questions