Go 使用反射设置nil*int32结构字段
我试图通过反射设置aGo 使用反射设置nil*int32结构字段,go,reflection,Go,Reflection,我试图通过反射设置anil*int的值 在下面的示例中,replaceNilWithNegativeOne应将任何nil*int32字段(标记为grib:“foo”)替换为指向-1的指针 但是,当代码运行时,reflect会因使用不可寻址的值设置而陷入恐慌状态panic:reflect:reflect.Value.Set 我在其他几个地方看到了我在这里提出的几乎完全相同的问题,例如: 以及非SO研究 我知道答案一定在那些回答中的某个地方,但我仍然无法将这些点连接起来。除了在下面的示例
nil
*int
的值
在下面的示例中,replaceNilWithNegativeOne
应将任何nil
*int32
字段(标记为grib:“foo”
)替换为指向-1的指针
但是,当代码运行时,reflect会因使用不可寻址的值设置而陷入恐慌状态panic:reflect:reflect.Value.Set
我在其他几个地方看到了我在这里提出的几乎完全相同的问题,例如:
- 以及非SO研究
fieldPtr.CanSet()==false
,但是,既然如此,我该如何实现我想要实现的目标呢
示例
// https://play.golang.org/p/yZOtYxwTzUs
package main
import (
"log"
"reflect"
"strings"
)
func main() {
type testStruct struct {
SomeField *int32 `grib:"foo"`
}
testStructInstance := testStruct{
SomeField: nil,
}
replaceNilWithNegativeOne(testStructInstance)
if *testStructInstance.SomeField != int32(-1) {
// We never get here
log.Println("Didn't get set")
}
}
func replaceNilWithNegativeOne(obj interface{}) (err error) {
objType := reflect.TypeOf(obj)
for i := 0; i < objType.NumField(); i++ {
if t, ok := objType.Field(i).Tag.Lookup("grib"); ok {
if strings.Contains(t, "foo") {
fieldPtr := reflect.ValueOf(obj).Field(i)
if fieldPtr.Kind() != reflect.Ptr {
// do some stuff
break
}
if fieldPtr.IsNil() {
v := -1
// I know this isn't working because the CanSet() == false
// But I want to set the value to -1.
fieldPtr.Set(reflect.ValueOf(&v))
continue
}
}
}
}
return
}
//https://play.golang.org/p/yZOtYxwTzUs
包干管
进口(
“日志”
“反映”
“字符串”
)
func main(){
类型testStruct struct{
SomeField*int32`grib:“foo”`
}
testStructInstance:=testStruct{
SomeField:零,
}
replaceNilWithNegativeOne(testStructInstance)
如果*testStructInstance.SomeField!=int32(-1){
//我们永远都到不了这里
log.Println(“未设置”)
}
}
func replaceNilWithNegativeOne(obj接口{})(错误){
objType:=reflect.TypeOf(obj)
对于i:=0;i
这里有两个问题。第一个是需要一个值。将指向结构的指针传递给函数,而不是结构值:
replaceNilWithNegativeOne(&testStructInstance)
在函数中,调用以获取结构的反射值
另一个问题是代码将int赋值给int32。使用int32(-1)修复此问题
以下是更新后的函数,其中包含以下更改:
replaceNilWithNegativeOne(obj interface{}) (err error) {
v := reflect.ValueOf(obj).Elem()
t := v.Type()
for i := 0; i < t.NumField(); i++ {
if grib, ok := t.Field(i).Tag.Lookup("grib"); ok {
if strings.Contains(grib, "foo") {
fv := v.Field(i)
if fv.Kind() != reflect.Ptr {
// do some stuff
break
}
if fv.IsNil() {
iv := int32(-1)
fv.Set(reflect.ValueOf(&iv))
continue
}
}
}
}
return nil
}
replaceNilWithNegativeOne(obj接口{})(错误){
v:=reflect.ValueOf(obj).Elem()
t:=v.Type()
对于i:=0;i