tydldd 2020-04-23
反射
import ( "fmt" "reflect" ) func TestType(a interface{}) { //获取类型(静态信息) t := reflect.TypeOf(a) kind := t.Kind() switch kind { case reflect.Int: fmt.Printf("a is a int\n") a = 2 case reflect.String: fmt.Printf("a is a string\n") } fmt.Printf("t=%v,kind=%v\n\n",t,kind) } func TestValue(a interface{}) { v := reflect.ValueOf(a) //kind := v.Kind() t := v.Type() switch t.Kind() { case reflect.Int: fmt.Printf("a is a int\n") v.SetInt(10000) case reflect.String: v.SetString("xxx") fmt.Printf("a is a string\n") case reflect.Ptr: t1 := v.Elem().Type() switch (t1.Kind()) { case reflect.Int: v.Elem().SetInt(100) fmt.Printf("ptn is int \n") case reflect.String: v.Elem().SetString("hello") fmt.Printf("ptn is string\n") } fmt.Printf("a=%v is a point type\n",t1) } fmt.Printf("v=%v,kind=%v\n\n",v,t) } func main() { //var a int //TestType(a) //fmt.Printf("a=%v\n",a) //var b string //TestType(b) var c int TestValue(&c) var d string TestValue(&d) fmt.Printf("c=%v, d=%v\n",c,d) }
type Users struct { Name string `json:"name"` Age int Sex string } //1. 获取a的类型 //2. 我要动态改变a里面存的值 //3. 如果a里面存储的是一个结构体,那可以通过反射获取结构体中的字段信息以及调用结构体里面的方法 func TestValueStruct(a interface{}) { v := reflect.ValueOf(a) t := v.Type() switch t.Kind() { case reflect.Struct: fieldNum := t.NumField() fmt.Printf("field num:%d\n", fieldNum) for i := 0; i <fieldNum; i++{ field := t.Field(i) vField := v.Field(i) fmt.Printf("field[%d] name:%s, json key:%s, val:%v\n", i, field.Name, field.Tag.Get("json"), vField.Interface()) } } } func main() { var user Users user.Name = "xxx" user.Age = 100 user.Sex = "man" TestValueStruct(user) fmt.Printf("user:%#v\n", user) }
type S struct { A int B string } func (s *S) Test() { fmt.Printf("this is a test\n") } func (s *S) SetA (a int) { s.A = a } func main() { s := S{23,"abc"} v := reflect.ValueOf(&s) m := v.MethodByName("Test") var args1 []reflect.Value m.Call(args1) setA := v.MethodByName("SetA") var args2 []reflect.Value args2 = append(args2,reflect.ValueOf(100)) setA.Call(args2) #修改结构体中的值 fmt.Printf("s:%#v\n",s) }
总结:
json序列化简版代码
package json_reflect import ( "fmt" "reflect" ) func Marshals(data interface{}) (jsonStr string) { t := reflect.TypeOf(data) v := reflect.ValueOf(data) switch t.Kind(){ case reflect.String,reflect.Int,reflect.Int32: jsonStr = fmt.Sprintf("\"%v\"", data) case reflect.Struct: numField := t.NumField() for i := 0; i < numField; i++ { //类型信息 name := t.Field(i).Name tag := t.Field(i).Tag.Get("json") if len(tag) > 0 { name = tag } //值信息 vField := v.Field(i) vFieldValue := vField.Interface() //拼接json if t.Field(i).Type.Kind() == reflect.String { jsonStr += fmt.Sprintf("\"%s\":\"%v\"", name, vFieldValue) } else { jsonStr += fmt.Sprintf("\"%s\":%v", name, vFieldValue) } if i != numField - 1 { jsonStr += "," } } jsonStr = "{" +jsonStr + "}" } return }
测试代码
package main import ( "fmt" "oldBoy/day9/json_reflect" ) type User struct { Name string `json:"name"` Age int `json:"age"` Sex string `json:"sex"` } func main() { var a string = "hello abc" jsonStr := json_reflect.Marshals(a) fmt.Printf(jsonStr) var user User user.Name = "aaa" user.Age = 10 user.Sex = "male" jsonStr = json_reflect.Marshals(user) fmt.Printf(jsonStr) }