golang之reflect
reflect,反射。
利用reflect,可以得到一个struct的相关信息。
package main import (
"fmt"
"reflect"
) type User struct {
Id int
Name string
Age int
} func (u User) Hello(name string) {
fmt.Printf("hello %s, my name is %s\n", name, u.Name)
} type Manager struct {
User
title string
} func main() {
// modify variable through reflect
//x := 123
//v := reflect.ValueOf(&x)
//v.Elem().SetInt(234)
//fmt.Println(x) u := User{1, "xiaoming", 12}
u.Hello("atom") // call method through reflect
v := reflect.ValueOf(u)
mv := v.MethodByName("Hello")
args := []reflect.Value{reflect.ValueOf("jack")}
mv.Call(args) Info(u)
Set(&u)
Info(u) m := Manager{User{1, "xiaoming", 12}, "rd"}
// get nested struct field
t := reflect.TypeOf(m)
fmt.Printf("%#v\n", t.Field(0))
fmt.Printf("%#v\n", t.FieldByIndex([]int{0,0}))
} func Info(i interface{}) {
t := reflect.TypeOf(i) if t.Kind() != reflect.Struct {
fmt.Println("Type Error")
return
}
fmt.Println("Type:", t.Name()) v := reflect.ValueOf(i) // get fields
fmt.Println("Fields:")
for i := 0; i < t.NumField(); i++ {
f := t.Field(i)
val := v.Field(i).Interface()
fmt.Printf("%6s: %v = %v\n", f.Name, f.Type, val)
}
// get methods
fmt.Println("Methods:")
for i := 0; i < t.NumMethod(); i++ {
m := t.Method(i)
fmt.Printf("%6s: %v\n", m.Name, m.Type)
}
} func Set(i interface{}) {
v := reflect.ValueOf(i)
if v.Kind() != reflect.Ptr || !v.Elem().CanSet() {
fmt.Println("Error")
return
} else {
v = v.Elem()
} f := v.FieldByName("Name")
if !f.IsValid() {
fmt.Println("Bad Field")
}
if f.Kind() == reflect.String {
f.SetString("byebye")
}
}
输出如下:
hello atom, my name is xiaoming
hello jack, my name is xiaoming
Type: User
Fields:
Id: int = 1
Name: string = xiaoming
Age: int = 12
Methods:
Hello: func(main.User, string)
Type: User
Fields:
Id: int = 1
Name: string = byebye
Age: int = 12
Methods:
Hello: func(main.User, string)
reflect.StructField{Name:"User", PkgPath:"", Type:(*reflect.rtype)(0x10d9e00), Tag:"", Offset:0x0, Index:[]int{0}, Anonymous:true}
reflect.StructField{Name:"Id", PkgPath:"", Type:(*reflect.rtype)(0x10c4e60), Tag:"", Offset:0x0, Index:[]int{0}, Anonymous:false}
需要注意的一个地方是:
结构体的field首字母需要大写,否则会报错"panic: reflect.Value.Interface: cannot return value obtained from unexported field or method"
参考资料
golang之reflect的更多相关文章
- golang:reflect反射
因为之前一直以C++为主要开发语言,所以刚接触go语言中的reflect时感觉很懵逼,因此决定找资料彻底学习一下. 到底反射是什么? https://blog.golang.org/laws-of-r ...
- golang基础--reflect反射
反射的知识点比较晦涩,后期会对此知识点展开深入的分析及示例代码展示 反射可达大提高程序的灵活性,使得inferface{}有更大的发挥余地 反射使用TypeOf和ValueOf函数从接口中获取目标对象 ...
- golang 使用reflect反射结构体
"反射结构体"是指在程序执行时,遍历结构体中的字段以及方法. 1.反射结构体 下面使用一个简单的例子说明如何反射结构体. 定义一个结构体,包括3个字段,以及一个方法. 通过refl ...
- Golang学习 - reflect 包
------------------------------------------------------------ 在 reflect 包中,主要通过两个函数 TypeOf() 和 ValueO ...
- 【玩转Golang】reflect.DeepEqual
如果有两个map,内容都一样,只有顺序不同 m1:=map[,,}; m2:=map[,,}; 我们怎么判断二者是否一致呢? 如果你打算这么写: fmt.Println("m1==m2&qu ...
- golang的reflect
引用自 http://www.jb51.net/article/115002.htm 和 C 数据结构一样,Go 对象头部并没有类型指针,通过其自身是无法在运行期获知任何类型相关信息的.反射操作所需要 ...
- golang 通过reflect反射修改值
不是所有的反射值都可以修改.对于一个反射值是否可以修改,可以通过CanSet()进行检查. 要修改值,必须满足: 可以寻址 可寻址的类型: 指针指向的具体元素 slice的元素 可寻址的结构体的字段( ...
- golang反射reflect机制用法
package main import ( "fmt" "reflect" ) type User struct { Id int Name string Ag ...
- Golang的反射reflect深入理解和示例
编程语言中反射的概念 在计算机科学领域,反射是指一类应用,它们能够自描述和自控制.也就是说,这类应用通过采用某种机制来实现对自己行为的描述(self-representation)和监测(examin ...
随机推荐
- 8.2 常见api:String类的使用
/* * String:字符串类 * 由多个字符组成的一串数据 * 字符串其本质是一个字符数组 * * 构造方法: * String(String original):把字符串数据封装成字符串对象 * ...
- "多行文本"组件:<multi> —— 快应用组件库H-UI
 <import name="multi" src="../Common/ui/h-ui/text/c_text_multi"></impo ...
- Python操作rabbitmq系列(四):根据类型订阅消息
在上一章中,所有的接收端获取的所有的消息.这一章,我们将讨论,一些消息,仍然发送给所有接收端.其中,某个接收端,只对其中某些消息感兴趣,它只想接收这一部分消息.如下图:C1,只对error感兴趣,C2 ...
- python3(三)enc
# ASCII编码和Unicode编码的区别:ASCII编码是1个字节,而Unicode编码通常是2个字节. # Unicode把所有语言都统一到一套编码里,这样就不会再有乱码问题了. # 新的问题又 ...
- 自己总结 :并发队列ConcurrentLinkedQueue、阻塞队列AraayBlockingQueue、阻塞队列LinkedBlockingQueue 区别 和 使用场景总结
并发队列ConcurrentLinkedQueue.阻塞队列AraayBlockingQueue.阻塞队列LinkedBlockingQueue 区别 和 使用场景总结 分类: Java2013-0 ...
- CVE-2020-1938:Apache-Tomcat-Ajp漏洞-复现
0x00 漏洞简介 Apache与Tomcat都是Apache开源组织开发的用于处理HTTP服务的项目,两者都是免费的,都可以做为独立的Web服务器运行. Apache Tomcat服务器存在文件包含 ...
- 干货:python面对对象类继承简介
前言 文的文字及图片来源于网络,仅供学习.交流使用,不具有任何商业用途,版权归原作者所有,如有问题请及时联系我们以作处理. 作者:python视觉算法 PS:如有需要Python学习资料的小伙伴可以加 ...
- CTF中的命令执行绕过
本位原创作者:Smity 在介绍命令注入之前,有一点需要注意:命令注入与远程代码执行不同.他们的区别在于,远程代码执行实际上是调用服务器网站代码进行执行,而命令注入则是调用操作系统命令进行执行. 作为 ...
- 通过dockerfile制作镜像
Dockerfile是一个用于构建Docker镜像的文本文件,其中包含了创建Docker镜像的全部指令.就是将我们安装环境的每个步骤使用指令的形式存放在一个文件中,最后生成一个需要的环境. Docke ...
- winfrom 基础
1 winfrom就是一种窗体开发端应用程序 2 窗体分类 1)记事本类:可以最大最小化,可以拖拽 窗体默 ...