Pattern matching in Rust maakt het mogelijk om waarden op structuur te splitsen, complexe typen te analyseren en te verwerken met behulp van constructies zoals match, if let, while let. Destructurering (opdelen in delen) is handig voor het werken met tuples, structuren, enums en zelfs verwijzingen.
Voorbeeld met enum:
enum Message { Quit, ChangeColor(i32, i32, i32), Write(String), } let m = Message::ChangeColor(255, 0, 0); match m { Message::Quit => println!("Quit!"), Message::ChangeColor(r, g, b) => println!("Color: {} {} {}", r, g, b), Message::Write(text) => println!("Text: {}", text), }
Destructurering van structuren:
struct Point { x: i32, y: i32 } let p = Point { x: 10, y: 20 }; let Point { x, y } = p;
Nuances:
ref en ref mut maakt het mogelijk om verwijzingen te krijgen bij het splitsen.@ kan een deel van het patroon "hernoemd" worden.if guard).&SomeType) is het belangrijk om eigendom en borrowing te onthouden.Kan "_" (onderstreping) altijd worden gebruikt om delen van een patroon te negeren en compiler waarschuwingen te vermijden?
Niet altijd. Onderstreping negeert inderdaad een waarde, maar als niet alle opties van de enum worden verwerkt en "_" wordt gebruikt als catch-all, kun je nieuwe opties mislopen bij het uitbreiden van de enum in de toekomst. Het is beter om altijd expliciet belangrijke opties op te sommen, zodat de compiler kan waarschuwen voor onbeschouwde gevallen!
match result { Ok(val) => ..., Err(err) => ..., //_ => ... // niet aanbevolen voor enum! }
Verhaal
In een IoT-applicatie stopte het apparaat met reageren omdat een nieuwe optie in de enum was toegevoegd met catch-all "_" in plaats van expliciet alle opties te behandelen. De fout bleef onopgemerkt tot de uitrol. Na dit voorval werden kritische enums altijd alleen expliciet behandeld met een drievoudig patroon.
Verhaal
Voor een complexe structuur met geneste tuples werd de syntax van destructurering van recursieve velden vergeten, en in plaats van verwijzingen te verkrijgen, klonen de codes per ongeluk grote objecten, wat leidde tot prestatieverlies.
Verhaal
In een functie voor het verzenden van berichten tussen threads werd destructurering via if-let gebruikt, maar werden zeldzame opties van de enum genegeerd. Bij het verschijnen van nieuwe bedrijfslogica gingen berichten gewoon verloren. Na dit voorval werd het in het team vastgesteld als regel dat elk match-expressie volledig moet zijn zonder catch-all.