Goの中ではtry catchがないです。
異常処理には、defer,panic,recoverで制御します。
defer
deferを実行した関数がリターンする直前に、指定した関数の呼び出しが行われるようにスケジューリングします
逆順で実行する流れです。
例:
func main() {
printNum()
}
func printNum() {
for i := 0; i < 5; i++ {
fmt.Println("数字:", i)
defer fmt.Println("defer:", i)
}
}
出力:
数字: 0
数字: 1
数字: 2
数字: 3
数字: 4
defer: 4
defer: 3
defer: 2
defer: 1
defer: 0
panic
panicを発生すると、その以降の処理は行わないです。
例:
func main() {
fmt.Println("Go begin")
defer fmt.Println("defer処理")
fmt.Println("ロジック処理 begin")
printNum()
fmt.Println("ロジック処理 end")
fmt.Println("Go end")
}
func printNum() {
for i := 0; i < 5; i++ {
fmt.Println("数字:", i)
if i == 2 {
panic("三番目に異常が発生しました。")
}
}
}
出力:
Go begin
ロジック処理 begin
数字: 0
数字: 1
数字: 2
defer処理
panic: 三番目に異常が発生しました。
goroutine 1 [running]:
main.printNum()
出力の通り、異常発生してもdefer部分が実行されます。
recover
recoverを呼び出すと、巻き戻しを停止し、panicに渡された引数が返ります
例:
func main() {
fmt.Println("Go begin")
defer func() {
if err := recover(); err != nil {
fmt.Println("defer エラー:", err)
fmt.Println("defer エラーが発生したため、ロジック処理は終了")
}
}()
fmt.Println("ロジック処理 begin")
printNum()
fmt.Println("ロジック処理 end")
fmt.Println("Go end")
}
func printNum() {
for i := 0; i < 5; i++ {
fmt.Println("数字:", i)
if i == 2 {
panic("三番目に異常が発生しました。")
}
}
}
出力:
Go begin
ロジック処理 begin
数字: 0
数字: 1
数字: 2
defer エラー: 三番目に異常が発生しました。
defer エラーが発生したため、ロジック処理は終了
以上