関数やメソットの引数が空インターフェースの場合、受け取った引数を使用する時にどのような型なのか分かりません。
従って、型を判断する必要があります。
Goにはインターフェースがどの型なのかを判定する方法があります。
なお、空インターフェースについては以下を参照して下さい。
型アサーションの基本
型アサーションを使用してインターフェースが実際にどの型なのかを判定します。
まず、型アサーションは以下の形式で期待する型を受け取れます。
期待する型 := 変数.(期待する型)
実際の型と期待する型が異なる場合パニックになってしまうのでカンマ ok イディオム を使って期待した型だったかを判定できます。
期待する型, 判定結果 := 変数.(期待する型)
型アサーションの例
以下は実際に型アサーションを使用してみました。
package main
import (
"fmt"
)
// インターフェースの定義
type myInterface interface {
getName() string
}
// 犬の構造体の定義
type dog struct {
name string
}
// 犬のメソット定義
func (d dog) getName() string {
return d.name
}
func main() {
d := dog{}
d.name = "dog_name"
determineType(d) // dog_name が表示される
i := 1
determineType(i) // 予期せぬ型です が表示される
}
func determineType(m interface{}) {
// 型アサーション。カンマ ok イディオム を使ってインターフェースの型を判定する
dog, ok := m.(dog)
if ok {
fmt.Println(dog.getName())
} else {
fmt.Println("予期せぬ型です")
}
}
determineType関数の引数は空インターフェースになっています。
determineType関数は型アサーションを使用して引数がdog型である場合、dog型のメソット(getName())を実行します。
main関数では、初めにdog型を使用してdetermineType関数を実行しています。この為、”dog_name” が表示されます。
次に、数値リテラルをを使用してdetermineType関数を実行しています。この為、”予期せぬ型です” が表示されます。