1# `map` for `Result` 2 3Panicking in the previous example's `multiply` does not make for robust code. 4Generally, we want to return the error to the caller so it can decide what is 5the right way to respond to errors. 6 7We first need to know what kind of error type we are dealing with. To determine 8the `Err` type, we look to [`parse()`][parse], which is implemented with the 9[`FromStr`][from_str] trait for [`i32`][i32]. As a result, the `Err` type is 10specified as [`ParseIntError`][parse_int_error]. 11 12In the example below, the straightforward `match` statement leads to code 13that is overall more cumbersome. 14 15```rust,editable 16use std::num::ParseIntError; 17 18// With the return type rewritten, we use pattern matching without `unwrap()`. 19fn multiply(first_number_str: &str, second_number_str: &str) -> Result<i32, ParseIntError> { 20 match first_number_str.parse::<i32>() { 21 Ok(first_number) => { 22 match second_number_str.parse::<i32>() { 23 Ok(second_number) => { 24 Ok(first_number * second_number) 25 }, 26 Err(e) => Err(e), 27 } 28 }, 29 Err(e) => Err(e), 30 } 31} 32 33fn print(result: Result<i32, ParseIntError>) { 34 match result { 35 Ok(n) => println!("n is {}", n), 36 Err(e) => println!("Error: {}", e), 37 } 38} 39 40fn main() { 41 // This still presents a reasonable answer. 42 let twenty = multiply("10", "2"); 43 print(twenty); 44 45 // The following now provides a much more helpful error message. 46 let tt = multiply("t", "2"); 47 print(tt); 48} 49``` 50 51Luckily, `Option`'s `map`, `and_then`, and many other combinators are also 52implemented for `Result`. [`Result`][result] contains a complete listing. 53 54```rust,editable 55use std::num::ParseIntError; 56 57// As with `Option`, we can use combinators such as `map()`. 58// This function is otherwise identical to the one above and reads: 59// Modify n if the value is valid, otherwise pass on the error. 60fn multiply(first_number_str: &str, second_number_str: &str) -> Result<i32, ParseIntError> { 61 first_number_str.parse::<i32>().and_then(|first_number| { 62 second_number_str.parse::<i32>().map(|second_number| first_number * second_number) 63 }) 64} 65 66fn print(result: Result<i32, ParseIntError>) { 67 match result { 68 Ok(n) => println!("n is {}", n), 69 Err(e) => println!("Error: {}", e), 70 } 71} 72 73fn main() { 74 // This still presents a reasonable answer. 75 let twenty = multiply("10", "2"); 76 print(twenty); 77 78 // The following now provides a much more helpful error message. 79 let tt = multiply("t", "2"); 80 print(tt); 81} 82``` 83 84[parse]: https://doc.rust-lang.org/std/primitive.str.html#method.parse 85[from_str]: https://doc.rust-lang.org/std/str/trait.FromStr.html 86[i32]: https://doc.rust-lang.org/std/primitive.i32.html 87[parse_int_error]: https://doc.rust-lang.org/std/num/struct.ParseIntError.html 88[result]: https://doc.rust-lang.org/std/result/enum.Result.html 89