Rust Error Handling
# Result Enum
Recoverable errors with Result
enum Result<T, E> {
Ok(T),
Err(E),
}
pub fn generate_nametag_text(name: String) -> Result<String, String> {
if name.is_empty() {
// Empty names aren't allowed.
Err(String::from("`name` was empty; it must be nonempty."))
} else {
Ok(format!("Hi! My name is {}", name))
}
}
# Ok
OkĀ variant indicates the operation was successful, and insideĀ OkĀ is the successfully generated value.
# Err
ErrĀ variant means the operation failed, andĀ ErrĀ contains information about how or why the operation failed.
# ? Operator
fn try_to_parse() -> Result<i32, ParseIntError> {
let x: i32 = "123".parse()?; // x = 123
let y: i32 = "24a".parse()?; // returns an Err() immediately
Ok(x + y) // Doesn't run.
}
let res = try_to_parse();
println!("{:?}", res);
Works with Option and ResultunwrapĀ orĀ return Err(From::from(err))
- Catch-all error
Under the hood, the?operator callsFrom::fromon the error value to convert it to a boxed trait object, aBox<dyn error::Error>. This boxed trait object is polymorphic, and since all errors implement theerror:Errortrait, we can capture lots of different errors in one “Box” object.
# Option Enum
fn main() {
enum Option<T> {
None, // NULL Equivalent
Some(T),
}
}
let x = Some("air");
assert_eq!(x.unwrap(), "air");
let maybe_name = Some(String::from("Alice"));
// Using `ref`, the value is borrowed, not moved ...
match maybe_name {
Some(ref n) => println!("Hello, {n}"),
_ => println!("Hello, world"),
}
// ... so it's available here!
println!("Hello again, {}", maybe_name.unwrap_or("world".into()));
Some()None