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