繁体   English   中英

golang reflect,获取指向struct字段值的指针

[英]golang reflect, get pointer to a struct field value

我正在尝试创建一个以mysql rows.Scan函数需要的方式转换结构的函数,因此我不需要手动传递大量参数。

注意:我知道sqlx的存在以及在每个指针的单独行中手动编写的替代方法,但是我想以这种方式解决它,因为我正在学习并想要了解正在发生的事情。

我用这个解决方案得到的错误是:
panic: sql: Scan error on column index 0: destination not a pointerpanic: sql: Scan error on column index 0: destination not a pointer看起来像valueField.Addr().Pointer()应该是指向值的指针。 以下是我的代码的简化。

type User struct {
    Name string
    Age  int
}

func StrutForScan(u interface{}) []interface{} {
    val := reflect.ValueOf(u).Elem()
    v := make([]interface{}, val.NumField())
    for i := 0; i < val.NumField(); i++ {
        valueField := val.Field(i)
        v[i] = valueField.Addr().Pointer()
    }
    return v
}

func ListUsers {
    rows, err := db.Query("SELECT * FROM users")
    PanicIf(err)
    var user User
    for rows.Next() {
        err := rows.Scan(StrutForScan(&user)...)
        PanicIf(err)
        fmt.Printf("\nName: %s, Age: %s", user.Name, string(user.Age))

    }
}

你需要使用.Interface()而不是.Pointer()

func StrutForScan(u interface{}) []interface{} {
    val := reflect.ValueOf(u).Elem()
    v := make([]interface{}, val.NumField())
    for i := 0; i < val.NumField(); i++ {
        valueField := val.Field(i)
        v[i] = valueField.Addr().Interface()
    }
    return v
}

这背后的原因是.Pointer()返回一个实际的“指针”指向数据,如果不使用unsafe包,你就无法做很多事情。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM