首页 >后端开发 >Golang >如何通过引用传递嵌套结构进行反射?

如何通过引用传递嵌套结构进行反射?

Mary-Kate Olsen
Mary-Kate Olsen原创
2024-10-24 01:49:01570浏览

How to Pass Nested Structures by Reference for Reflection?

通过引用传递嵌套结构进行反射

简介

考虑以下客户和联系人数据结构:

<code class="go">type Client struct {
    Id                int
    Age               int
    PrimaryContact    Contact
    Name              string
}

type Contact struct {
    Id        int
    ClientId  int
    IsPrimary bool
    Email     string
}</code>

我们的目标是使用反射来迭代所有客户端结构字段,为原始字段设置默认值,并递归地将相同的步骤应用于任何嵌套结构字段。但是,在尝试为 PrimaryContact 字段设置值时,我们遇到了“reflect.Value.Set using unaddressable value”恐慌。

通过引用传递

问题的出现是因为PrimaryContact 通过值而不是通过引用传递。为了解决这个问题,我们必须通过引用传递 PrimaryContact。为此,我们使用 Value.Addr() 来获取结构体字段的指针值。

解决方案

以下代码演示了如何通过引用传递 PrimaryContact:

<code class="go">func setDefaultValue(v reflect.Value) error {
    if v.Kind() != reflect.Ptr {
        return errors.New("Not a pointer value")
    }
    v = reflect.Indirect(v)
    
    // ... (same code as before)
    
    case reflect.Struct:
        for i := 0; i < v.NumField(); i++ {
            err := setDefaultValue(v.Field(i).Addr())
            if err != nil {
                return err
            }
        }
    }
    
    return nil  
}</code>

通过使用 v.Field(i).Addr() 获取每个结构体字段的指针值,我们可以修改实际的结构体字段而不是副本。

示例

为了说明解决方案,让我们考虑以下客户端实例:

<code class="go">a := Client{}</code>

调用 SetDefault() 函数后,我们得到:

<code class="go">{Id:42 Age:42 PrimaryContact:{Id:42 ClientId:42 IsPrimary:true Email:Foo} Name:Foo}</code>

这表明嵌套的 PrimaryContact 结构字段也已设置为默认值。

以上是如何通过引用传递嵌套结构进行反射?的详细内容。更多信息请关注PHP中文网其他相关文章!

声明:
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系admin@php.cn