不能在用反射制作的切片上使用范围,然后通过 json.Unmarshal
Can't use range on slice made with reflect then passed json.Unmarshal
我从下面的代码中得到以下错误:
invalid indirect of typedSlice (type interface {})
cannot range over typedSlice (type interface {})
这让我感到困惑,因为 reflect.TypeOf(copy)
匹配 t
的类型。
func Unmarshal(t reflect.Type) []interface{} {
ret := []interface{}{}
s := `[{"Name":"The quick..."}]`
slice := reflect.Zero(reflect.SliceOf(t))
o := reflect.New(slice.Type())
o.Elem().Set(slice)
typedSlice := o.Interface()
json.Unmarshal([]byte(s), typedSlice)
fmt.Println(typedSlice) // &[{The quick...}]
fmt.Println(reflect.TypeOf(typedSlice)) //same type as t
fmt.Println(*typedSlice) // invalid indirect of copy (type interface {})
for _, l := range typedSlice { //cannot range over copy (type interface {})
ret = append(ret, &l)
}
return ret
}
我创建了一个 go playground 工作代码来提供帮助。
为什么这个切片打印出一种类型但编译成另一种类型?
invalid indirect of typedSlice (type interface {})
您不能取消引用 typedSlice
,因为它是一个 interface{}
。您必须使用类型断言
提取指针
realSlice := *typedSlice.(*[]Demo)
cannot range over typedSlice (type interface {})
同样,由于 typedSlice
是一个 interface{}
,您不能对其进行范围调整。如果你想遍历需要使用类型断言的值,或者通过 reflect:
手动迭代
for i := 0; i < o.Elem().Len(); i++ {
ret = append(ret, o.Elem().Index(i).Interface())
}
我从下面的代码中得到以下错误:
invalid indirect of typedSlice (type interface {})
cannot range over typedSlice (type interface {})
这让我感到困惑,因为 reflect.TypeOf(copy)
匹配 t
的类型。
func Unmarshal(t reflect.Type) []interface{} {
ret := []interface{}{}
s := `[{"Name":"The quick..."}]`
slice := reflect.Zero(reflect.SliceOf(t))
o := reflect.New(slice.Type())
o.Elem().Set(slice)
typedSlice := o.Interface()
json.Unmarshal([]byte(s), typedSlice)
fmt.Println(typedSlice) // &[{The quick...}]
fmt.Println(reflect.TypeOf(typedSlice)) //same type as t
fmt.Println(*typedSlice) // invalid indirect of copy (type interface {})
for _, l := range typedSlice { //cannot range over copy (type interface {})
ret = append(ret, &l)
}
return ret
}
我创建了一个 go playground 工作代码来提供帮助。
为什么这个切片打印出一种类型但编译成另一种类型?
invalid indirect of typedSlice (type interface {})
您不能取消引用 typedSlice
,因为它是一个 interface{}
。您必须使用类型断言
realSlice := *typedSlice.(*[]Demo)
cannot range over typedSlice (type interface {})
同样,由于 typedSlice
是一个 interface{}
,您不能对其进行范围调整。如果你想遍历需要使用类型断言的值,或者通过 reflect:
for i := 0; i < o.Elem().Len(); i++ {
ret = append(ret, o.Elem().Index(i).Interface())
}