Go でインターフェース型の reflect.Type を取得する方法
Go の reflect パッケージを使っていて、ときどき操作している変数型との比較のために error などのインターフェース型の reflect.Type がほしいことがあるのだけれど、これは reflect.TypeOf((*error)(nil)).Elem() のように書くことで得られる。つまり、
nilをほしい型のポインタ型に変換- それを
reflect.TypeOfに渡してポインタ型のreflect.Typeを取得し Elem()でポインタをデリファレンスしてできる基本型のreflect.Typeを得る
という流れ。 Go の公式パッケージではよく見かける書法。これを使うと、たとえば変数が error インターフェースを満たすかどうかの判定は
package main
import (
"errors"
"fmt"
"reflect"
)
func main() {
err := errors.New("A problem occurs")
et := reflect.TypeOf(err)
if et.Implements(reflect.TypeOf((*error)(nil)).Elem()) {
fmt.Println("This is an error type")
} else {
fmt.Println("This isn't an error type")
}
}
のように書ける。もちろん、これはリフレクションを操作してる時の話で、普通は
package main
import (
"errors"
"fmt"
)
func main() {
err := errors.New("A problem occurs")
if _, ok := err.(error); ok {
fmt.Println("This is an error type")
} else {
fmt.Println("This isn't an error type")
}
}
とするのがよい