Einführung
In diesem Lab untersuchen wir die Result-Enumeration in Rust, die uns ermöglicht, den Erfolg oder das Scheitern einer Operation auszudrücken, indem wir entweder Ok mit einem Wert oder Err mit einer Erklärung des Fehlers zurückgeben.
Hinweis: Wenn das Lab keinen Dateinamen angibt, können Sie einen beliebigen Dateinamen verwenden. Beispielsweise können Sie
main.rsverwenden und es mitrustc main.rs &&./mainkompilieren und ausführen.
Result
Wir haben gesehen, dass die Option-Enumeration als Rückgabewert von Funktionen verwendet werden kann, die fehlschlagen können, wobei None zurückgegeben werden kann, um ein Fehlerzustand anzuzeigen. Manchmal ist es jedoch wichtig, warum eine Operation fehlschlägt zu erklären. Dazu haben wir die Result-Enumeration.
Die Result<T, E>-Enumeration hat zwei Varianten:
Ok(value), was angibt, dass die Operation erfolgreich war, und umschließt den von der Operation zurückgegebenenvalue. (valuehat den TypT)Err(why), was angibt, dass die Operation fehlgeschlagen ist, und umschließtwhy, das (hoffentlich) die Ursache des Fehlers erklärt. (whyhat den TypE)
mod checked {
// Mathematische "Fehler", die wir fangen möchten
#[derive(Debug)]
pub enum MathError {
DivisionByZero,
NonPositiveLogarithm,
NegativeSquareRoot,
}
pub type MathResult = Result<f64, MathError>;
pub fn div(x: f64, y: f64) -> MathResult {
if y == 0.0 {
// Diese Operation würde `fehlschlagen`, stattdessen geben wir den Grund
// des Fehlers in `Err` zurück
Err(MathError::DivisionByZero)
} else {
// Diese Operation ist gültig, geben wir das Ergebnis in `Ok` zurück
Ok(x / y)
}
}
pub fn sqrt(x: f64) -> MathResult {
if x < 0.0 {
Err(MathError::NegativeSquareRoot)
} else {
Ok(x.sqrt())
}
}
pub fn ln(x: f64) -> MathResult {
if x <= 0.0 {
Err(MathError::NonPositiveLogarithm)
} else {
Ok(x.ln())
}
}
}
// `op(x, y)` === `sqrt(ln(x / y))`
fn op(x: f64, y: f64) -> f64 {
// Dies ist eine dreistufige Match-Pyramide!
match checked::div(x, y) {
Err(why) => panic!("{:?}", why),
Ok(ratio) => match checked::ln(ratio) {
Err(why) => panic!("{:?}", why),
Ok(ln) => match checked::sqrt(ln) {
Err(why) => panic!("{:?}", why),
Ok(sqrt) => sqrt,
},
},
}
}
fn main() {
// Wird dies fehlschlagen?
println!("{}", op(1.0, 10.0));
}
Zusammenfassung
Herzlichen Glückwunsch! Sie haben das Result-Lab abgeschlossen. Sie können in LabEx weitere Labs absolvieren, um Ihre Fähigkeiten zu verbessern.