called `Result::unwrap()` on an `Err` value パニックの原因と直し方
文字列を数値に変換するparse()などはResult<T, E>型を返します。変換に失敗してErrになった状態でunwrap()を呼ぶと、パニックが発生します。
エラーメッセージの読み方
thread 'main' panicked at main.rs:3:32:
main.rs- ファイル名
3- 行番号 — 実際にクラッシュした行
32- 列番号
panicked- パニック — 実行時に回復不能な状態になったことを示します。tryやResultで捕まえない限り、そのままプロセスが終了します
called `Result::unwrap()` on an `Err` value: ParseIntError { kind: InvalidDigit }- 詳細メッセージ — どの値が問題だったか
このエラーが出る典型パターン
パターン1
1 fn main() { 2 let input = "abc "; ^ 3 let n: i32 = input.parse().unwrap(); 4 println!("{}", n); 5 }
thread 'main' panicked at main.rs:3:32:
called `Result::unwrap()` on an `Err` value: ParseIntError { kind: InvalidDigit }
parse()は変換できない文字列に対してErrを返します。Errの状態でunwrap()するとパニックします。
直し方: abc を 42 にします。
広告
広告スロット(未設定)
パターン2
1 fn main() { 2 let input = "hello"; ^ 3 let n: i32 = input.parse().unwrap(); 4 println!("{}", n); 5 }
thread 'main' panicked at main.rs:3:32:
called `Result::unwrap()` on an `Err` value: ParseIntError { kind: InvalidDigit }
数値に見えない文字列をparseすると必ずErrになり、そのままunwrap()すればパニックします。
直し方: hello を 100 にします。
パターン3
1 fn main() { 2 let input = "twelve"; ^ 3 let n: i32 = input.parse().unwrap(); 4 println!("{}", n); 5 }
thread 'main' panicked at main.rs:3:32:
called `Result::unwrap()` on an `Err` value: ParseIntError { kind: InvalidDigit }
ユーザー入力を数値として扱う前には、parseの結果がOkかErrかを必ず確認する必要があります。
直し方: twelve を 12 にします。
パターン4
1 fn main() { 2 let input = "n/a"; ^ 3 let n: i32 = input.parse().unwrap(); 4 println!("{}", n); 5 }
thread 'main' panicked at main.rs:3:32:
called `Result::unwrap()` on an `Err` value: ParseIntError { kind: InvalidDigit }
空文字や記号が混ざった文字列も数値として解釈できず、parseはErrを返します。
直し方: n/a を 7 にします。
パターン5
1 fn main() { 2 let input = "unknown"; ^ 3 let n: i32 = input.parse().unwrap(); 4 println!("{}", n); 5 }
thread 'main' panicked at main.rs:3:32:
called `Result::unwrap()` on an `Err` value: ParseIntError { kind: InvalidDigit }
parseの戻り値はResultであり、失敗する可能性が型として表現されています。
直し方: unknown を 99 にします。
よくある誤解
「parse()は文字列を数値に変換するだけの単純な処理のはず」という思い込みは誤りです。数値に変換できない文字列が渡される可能性がある限り、戻り値はResultとして失敗も表現されます。
まとめ
called `Result::unwrap()` on an `Err` value パニックの原因と直し方は初級でつまずきやすい項目です。上の5パターンを実際に手で直すと、エラーメッセージのどこを読めばよいかが掴めます。