import (
"reflect"
"testing"
)
type Users struct {
ID int
Name string
}
type TestInterface interface {
GetName() string
}
func (u *Users) UpdateName(newName string) {
u.Name = newName
}
func (u *Users) GetName() string {
return u.Name
}
func TestReflect(t *testing.T) {
u := Users{1, "mike"}
//返回指定對象的Kind類型
t.Log(reflect.TypeOf(32).Kind())
t.Log(reflect.ValueOf(32).Kind())
//根據方法名找方法
t.Log(reflect.TypeOf(&u).MethodByName("UpdateName"))
t.Log(reflect.ValueOf(&u).MethodByName("UpdateName"))
//返回第i個方法
t.Log(reflect.TypeOf(&u).Method(0))
t.Log(reflect.ValueOf(&u).Method(0))
//返回擁有的方法總數,包括unexported方法
t.Log(reflect.TypeOf(&u).NumMethod())
t.Log(reflect.ValueOf(&u).NumMethod())
//取struct結構的第n個field
t.Log(reflect.TypeOf(u).Field(0))
t.Log(reflect.ValueOf(u).Field(1))
//嵌套的方式取struct的field,比如v.FieldByIndex(1,2,3)等價於 v.field(1).field(2).field(3)
t.Log(reflect.TypeOf(u).FieldByIndex([]int{0}))
t.Log(reflect.ValueOf(u).FieldByIndex([]int{0}))
//返回名稱匹配match函數的field
t.Log(reflect.TypeOf(u).FieldByName("ID"))
t.Log(reflect.ValueOf(u).FieldByName("Name"))
//返回struct所包含的field數量
t.Log(reflect.TypeOf(u).NumField())
t.Log(reflect.ValueOf(u).NumField())
//分配內存時的內存對齊字節數
t.Log(reflect.TypeOf(u).Align())
//作為struct的field時內存對齊字節數
t.Log(reflect.TypeOf(u).FieldAlign())
//type名 string類型
t.Log(reflect.TypeOf(u).Name())
//包路徑, "encoding/base64", 內置類型返回empty string
t.Log(reflect.TypeOf(u).PkgPath())
//該類型變量占用字節數
t.Log(reflect.TypeOf(u).Size())
//type的string表示方式
t.Log(reflect.TypeOf(u).String())
//判斷該類型是否實現了某個接口
t.Log(reflect.TypeOf(u).Implements(reflect.TypeOf((*TestInterface)(nil)).Elem()))
//判斷該類型能否賦值給某個類型
t.Log(reflect.TypeOf(u).AssignableTo(reflect.TypeOf(Users{})))
//判斷該類型能否轉換為另外一種類型
t.Log(reflect.TypeOf(u).ConvertibleTo(reflect.TypeOf(1)))
//判斷該類型變量是否可以比較
t.Log(reflect.TypeOf(u).Comparable())
//取該類型的元素,指針指向的結構
t.Log(reflect.TypeOf(&u).Elem())
//調用函數
t.Log(reflect.ValueOf(&u).MethodByName("GetName").Call([]reflect.Value{}))
//判斷能否取地址
t.Log(reflect.ValueOf(&u).CanAddr())
//判斷Interface方法能否使用
t.Log(reflect.ValueOf(&u).CanInterface())
//判斷值能否改變
t.Log(reflect.ValueOf(&u).CanSet())
a := []int{0, 1}
//獲取容量 Array/Chan/Slice
t.Log(reflect.ValueOf(a).Cap())
c := make(chan int)
//關閉channel
reflect.ValueOf(c).Close()
//返回指針實際的值
t.Log(reflect.ValueOf(&u).Elem())
//索引操作 Array/Slice/String
t.Log(reflect.ValueOf(a).Index(0))
//修改數組第一個索引的值
reflect.ValueOf(a).Index(0).Set(reflect.ValueOf(1))
t.Log(a[0])
//將當前value以interface形式返回
t.Log(reflect.ValueOf(&u).Interface())
//判斷是否為nil,chan, func, interface, map, pointer, or slice valu
t.Log(reflect.ValueOf(&u).IsNil())
//是否是可操作的Value,返回false表示為zero Value
t.Log(reflect.ValueOf(&u).IsValid())
//獲取長度,適用於Array, Chan, Map, Slice, or String
t.Log(reflect.ValueOf(a).Len())
m := map[int]string{1: "Mike", 2: "Tom"}
//對map類型按key取值
t.Log(reflect.ValueOf(m).MapIndex(reflect.ValueOf(1)))
//map類型的所有key的列表
for index, key := range reflect.ValueOf(m).MapKeys() {
t.Log("key=", key)
t.Log("idnex=", index)
}
//返回value的Type
t.Log(reflect.ValueOf(1).Type())
}