Go/defer,panicとrecover

出典: フリー教科書『ウィキブックス(Wikibooks)』
< Go


defer,panicとrecover[編集]

Goでは、ゼロ除算のような例外が発生すると、組み込み関数 panicが呼び出されます(ランタイム・パニック)。

標準状態ではプログラムが終了しますが、deferで登録された関数(またはメソッド)は、panicが発生したときにも呼び出されます。deferの中で組み込み関数recoverを呼び出すと、panicの引数を得ることができます。

defer、panic、recoverによる例外処理は強力ですが、構造化されていないため、パッケージのAPIとして使用するには適していません。したがって、パッケージを超えて使用することは避けるべきです。

パッケージを超えたエラー処理には、type error interfaceが適しています。

コード例
package main

import "fmt"

func main() {
	defer func() {
		if err := recover(); err != nil {
			fmt.Printf("%v -- recovered(main)\n", err)
		}
	}()

	fmt.Println(subr())
	panic("User raised panic")
	fmt.Println("fin")
}

func subr() (i int) {
	defer func() {
		if err := recover(); err != nil {
			fmt.Printf("%v -- recovered(subr)\n", err)
			i = 0
		}
	}()
	a, b := 1, 0
	a = a / b
	fmt.Printf("a = %d, b = %d\n", a, b)
	return a
}
実行結果
./prog.go:13:2: unreachable code
Go vet exited.

runtime error: integer divide by zero -- recovered(subr)
0
User raised panic -- recoverd(main)

Program exited.