i’m trying to match two variables with elements of a tuple but I’m not sure what’s the error here.
fn main() {
let s = "cloudy";
let t = "warm";
let sky = ("cloudy", "sunny", "rainy");
let temperature = ("warm", "cold", "freezing");
match (s,t) {
(sky.0, temperature.0) => println!("It's cloudy and warm"),
}
}
>Solution :
According to the match expression documentation, the left side of a match expression needs to be a pattern.
Sadly, dynamic variables do not count as patterns. If you have a variable on the left side, the pattern matching will try to destructure data into it instead.
Solution #1: If Statements
If you absolutely need to match with a dynamic variable, the only way I see is to use if statements:
fn main() {
let s = "cloudy";
let t = "warm";
let sky = ("cloudy", "sunny", "rainy");
let temperature = ("warm", "cold", "freezing");
if s == sky.0 && t == temperature.0 {
println!("It's cloudy and warm")
}
}
Solution #2: Literals
If you want to do pattern matching on strings, you need to use string literals.
Further, the match statement needs to be exhaustive, meaning, it must cover every possibility. So in your case the easiest way to achieve that is to use the _ pattern to match everything that hasn’t been matched before.
This is also one of the reasons dynamic variables can’t be used in match patterns: The compiler does not yet know the content of those variables, so it cannot check if the match is exhaustive.
fn main() {
let s = "cloudy";
let t = "warm";
match (s, t) {
("cloudy", "warm") => println!("It's cloudy and warm"),
_ => println!("It isn't cloudy and warm"),
}
}
Solution #3: Enums
The third solution, and the one you probably intended to do by defining the sky and temperature variables, is to use enums.
But just as previously, the match statement needs to be exhaustive and therefore we need to add the _ case.
pub enum Sky {
Cloudy,
Sunny,
Rainy,
}
pub enum Temperature {
Warm,
Cold,
Freezing,
}
fn main() {
let s = Sky::Cloudy;
let t = Temperature::Warm;
match (s, t) {
(Sky::Cloudy, Temperature::Warm) => println!("It's cloudy and warm"),
_ => println!("It isn't cloudy and warm"),
}
}
If you have strings as input values, you can of course then implement the FromStr trait for those enums to convert the strings into an enum value.
