如何使用 Go 反射 pkg 获取切片结构字段的类型?

Posted

技术标签:

【中文标题】如何使用 Go 反射 pkg 获取切片结构字段的类型?【英文标题】:How to use Go reflection pkg to get the type of a slice struct field? 【发布时间】:2017-07-06 17:58:04 【问题描述】:

我正在尝试使用反射来构建一个例程,该例程将列出传入的任意结构中所有字段的名称、种类和类型。这是我目前所得到的:

type StatusVal int
type Foo struct 
    Name string
    Age  int

type Bar struct 
    Status StatusVal
    FSlice []Foo


func ListFields(a interface) 
    v := reflect.ValueOf(a).Elem()
    for j := 0; j < v.NumField(); j++ 
        f := v.Field(j)
        n := v.Type().Field(j).Name
        t := f.Type().Name()
        fmt.Printf("Name: %s  Kind: %s  Type: %s\n", n, f.Kind(), t)
    


func main() 
    var x Bar
    ListFields(&x)

输出如下:

Name: Status  Kind: int  Type: StatusVal
Name: FSlice  Kind: slice  Type: 

当字段为切片时,类型为空。我尝试了几种方法来获取切片的数据类型,但所有尝试都导致恐慌......通常是这个:

reflect: call of reflect.Value.Elem on slice Value

需要对此代码进行哪些更改,以便在输出中列出所有字段(包括切片)的类型?

这里是操场链接:https://play.golang.org/p/zpfrYkwvlZ

【问题讨论】:

【参考方案1】:

type literal 中给出的 slice 类型如 []Foo未命名 类型,因此 Type.Name() 返回一个空字符串 ""

改用Type.String()

t := f.Type().String()

然后是输出(在Go Playground 上试试):

Name: Status  Kind: int  Type: main.StatusVal
Name: FSlice  Kind: slice  Type: []main.Foo

查看相关问题以了解有关类型及其名称的更多信息:Identify non builtin-types using reflect

【讨论】:

以上是关于如何使用 Go 反射 pkg 获取切片结构字段的类型?的主要内容,如果未能解决你的问题,请参考以下文章

Go 切片

go-反射

go语言系列-反射

GO之反射

反射以获取字段标记

go语言的reflect(反射)