反射:reflect

遍历结构体的字段,

调用结构体的方法

获取结构体标签的值

package main

import (
    "fmt"
    "reflect"
)

type Monster struct {
    Name  string  `json:"name"`
    Age   int     `json:"age"`
    Score float64 `json:"score"`
    Sex   string  `json:"sex"`
}

func (m Monster) GetSum(n1 int, n2 int) int {
    return n1 + n2
}

func (m Monster) Set(name string, age int, score float64, sex string) {
    m.Name = name
    m.Age = age
    m.Score = score
    m.Sex = sex
}

func (m Monster) Print() {
    fmt.Println("---start---")
    fmt.Println(m)
    fmt.Println("---end---")
}

//反射
func testStruct(b interface{}) {
    rTyp := reflect.TypeOf(b)  //main.Monster
    rVal := reflect.ValueOf(b) //{tom 20 20 nan}

    s := rTyp.Kind()  //struct
    kd := rVal.Kind() //struct

    //如果类别不是一个机构体就退出
    if kd != reflect.Struct {
        fmt.Println("expect struct")
    }

    fmt.Println(rTyp)
    fmt.Println(rVal)
    fmt.Println(s)
    fmt.Println(kd)

    num := rVal.NumField() //4
    fmt.Printf("一个有%v个字段\n", num)
    //获取字段的tag和字段的值
    for i := 0; i < num; i++ {
        fieldName := rTyp.Field(i).Tag.Get("json")
        fieldValue := rVal.Field(i)
        fmt.Printf("%v=%v\n", fieldName, fieldValue)
    }

    //操作方法
    methodNum := rVal.NumMethod() //小写的方法获取不到
    fmt.Printf("strust has %v个方法\n", methodNum)

    //方法的索引 是按ASCII码排序
    //func (v Value) Call(in []Value) []Value
    rVal.Method(1).Call(nil) //调用print方法

    //声明这种的切片 []reflect.Value
    var params []reflect.Value
    params = append(params, reflect.ValueOf(10))
    params = append(params, reflect.ValueOf(20))

    res := rVal.Method(0).Call(params)
    fmt.Printf("res=%v", res[0].Int())

}

func main() {
    m := Monster{
        Name:  "tom",
        Age:   10,
        Score: 20.0,
        Sex:   "男",
    }
    testStruct(m)
}
本作品采用《CC 协议》,转载必须注明作者和本文链接
有梦想的人睡不着,没有梦想的人睡不醒。
讨论数量: 0
(= ̄ω ̄=)··· 暂无内容!

讨论应以学习和精进为目的。请勿发布不友善或者负能量的内容,与人为善,比聪明更重要!
文章
84
粉丝
15
喜欢
120
收藏
232
排名:224
访问:4.0 万
私信
所有博文
博客标签
redis
1
php
1
laravel
7
docker
3
orm
2
sync
1
pivot
1
detach
2
attach
2
算法
1
递归
1
多对多
1
lnmp环境搭建
1
GO变量
1
GO数据类型
1
IOC注入反转
1
IOC容器的绑定解析过程(绑定单例)
1
原生微信网页授权登录(natapp穿墙)
1
VMwareNAT网卡配置
1
MySQL基础架构
1
redis 主从搭建
1
Sentinel哨兵模式解决故障转移
1
elasticsearch安装
1
elasticsearch集群安装3台
1
安装kibana
1
必须了解的mysql三大日志-binlog、redo log和undo log
1
何处理数据恢复 数据丢失 面试tx的架构师的岗位问的
1
分库分表插入数据
1
创建分库分表(在主从复制的基本上)
1
分库分表总结
1
mysql总结
1
haproxy状态检测脚本(完成高可用)
1
mysql高可用衡搭建(Keepalived)
1
mysql负载均衡搭建(haproxy)
1
mysql主从恢复数据一致性(pt工具-t-table-checksum和pt-table-sync)
1
终于解决了《====》记一次mysql热备份xtrabackup(没有解决问题)
1
mysql事务
1
MYSQL8.0安装
1
Redis-cluster分布式集群搭建部署
1
比Redis-cluster还好的redis分布式集群(twemproxy)
1
Redis缓存穿透/缓存雪崩/缓存击穿(案例:产生的原因 解决方案利/弊)
1
数据结构之MySQL独爱B+树(二叉树、AVL树、红黑树、B树对比)
1
B-tree
1
B+tree
1
Mycat实现mysql的负载均衡读写分离
2
mysql双主双从 搭建配置
1
mycat 双主双从-负载均衡-高可用
1
Mycat垂直分库
1
记一次mysql高可用技术分享
1
【rabbitmq】安装ampq的扩展的踩坑总结
1
PHP操作MongoDB(增删改查)
1
golang总结
5
社区赞助商