这是一个不起作用的简单go程序:
package main import "fmt" type Vertex struct { X int Y int } func main() { v := Vertex{1, 2} fmt.Println(getProperty(&v, "X")) } func getProperty(v *Vertex, property string) (string) { return v[property] }
错误:
prog.go:18:无效的操作:v [属性](*顶点类型的索引)
我想要的是使用名称访问Vertex X属性。如果我这样做,v.X它会起作用,但v["X"]不会。
v.X
v["X"]
有人可以告诉我如何进行这项工作吗?
大多数代码都不需要这种动态查找。与直接访问相比,它效率低下(编译器知道Vertex结构中X字段的偏移量,可以将vX编译为单个机器指令,而动态查找则需要某种哈希表实现或类似方法)。它还禁止静态类型输入:编译器无法检查您是否没有尝试动态访问未知字段,并且它不知道结果类型应该是什么。
但是…语言为您很少需要的时候提供了一个反射模块。
package main import "fmt" import "reflect" type Vertex struct { X int Y int } func main() { v := Vertex{1, 2} fmt.Println(getField(&v, "X")) } func getField(v *Vertex, field string) int { r := reflect.ValueOf(v) f := reflect.Indirect(r).FieldByName(field) return int(f.Int()) }
这里没有错误检查,因此如果您请求不存在的字段或者该字段的类型不是int,您将感到恐慌。检查文档以了解更多详细信息。