fn main() {
a();
}
fn a() {
let x = c().unwrap();
b(x);
}
fn b(n: u8) {
println!("{}", n);
}
fn c() -> Option<u8> {
None
}
Hi,the above code will panic because called Option::unwrap()
on a None
value' (c().unwrap()
),the way to avoid it is to change to unwrap_or
or unwrap_or_else
,to use them, you have to provide a default value,but I just want immediately to stop the execution of the function if the c()
is None
。A good way to do that maybe the pattern matching.
let x = match c() {
Some(v) => v,
None => {
return;
}
};
is possible have a method like:
let stop_the_fn=||{
println("Stop Immediately")
};
let x = c().unwrap_or_terminate(stop_the_fn);
A method on Option
won't be able to force the function that called it to return; that's just not how things work.
There's crates out there that provide a version of try!()
for options which return None
if the value passed to them is None
, but it looks like you just want to return nothing. You can make your own macro for this in a few lines:
macro_rules! unwrap_or_ret (
($opt:expr) => (
match $opt {
Some(val) => val,
None => return,
}
)
);
You can add an additional rule to run some code before returning:
macro_rules! unwrap_or_ret (
($opt:expr) => (
match $opt {
Some(val) => val,
None => return,
}
);
($opt:expr, $before_ret: expr) => (
match $opt {
Some(val) => val,
None => {
// Silence "unused value" warnings
let _ = $before_ret;
return;
}
);
);
Usage:
let x = c();
let val = unwrap_or_ret!(x);
// or
let val = unwrap_or_ret!(x, println!("Stop immediately!"));
// or (blocks are expressions, so this works
let val = unwrap_or_ret(x, {
println!("Stop immediately!");
println!("Value was None.");
});
1 Like
Alternatively you can use Result instead of Option. That allows you to use the try! macro
Rust Playground