英文:
Assign result of reflect.AppendSlice to pointer
问题
我遇到了一些困难,无法将这段代码转换为一个接受interface{}
作为输入参数的更通用的版本,该代码实际上是对一个切片进行左旋转。
我在最后的赋值语句上遇到了问题:
func rotateSlice(a interface{}, i int) {
v := reflect.ValueOf(a)
x, b := v.Elem().Slice(0, i), v.Elem().Slice(i, v.Elem().Len())
*a = reflect.AppendSlice(b, x)
}
错误信息是invalid indirect of a (type {})
。变量a
的值是interface{}
,因此*a =
将会将右侧的值赋给指针指向的空间。然而,我的AppendSlice
调用返回的是Value
类型。我不确定类型断言应该在哪里进行,我猜应该在左侧进行断言操作?
英文:
I have troubles translating this piece of code, which is effectively a left rotate on a slice, into a more generic version which accepts interface{}
as an input parameter.
func rotate(a *[]int, i int) {
x, b := (*a)[:i], (*a)[i:]
*a = append(b, x...)
}
I have troubles with the final assignment:
func rotateSlice(a interface{}, i int) {
v := reflect.ValueOf(a)
x, b := v.Elem().Slice(0, i), v.Elem().Slice(i, v.Elem().Len())
*a = reflect.AppendSlice(b, x)
}
The error message is invalid indirect of a (type {})
. The value of a
is interface{}
, hence *a =
would be to assign the right-hand value to the space where the pointer is pointing to. My call to AppendSlice
returns Value
though. I am not sure where the type assertion needs to happen, I suppose on the left-hand side?
答案1
得分: 1
在Go 1.18及更高版本中,通过使用泛型来消除reflect包的使用:
func rotateSlice[T any](a []T, i int) []T {
x, b := a[:i], a[i:]
return append(b, x...)
}
调用方式如下:x = rotateSlice(x, 2)
以下是使用reflect包实现rotate的方法。
使用Value.Set来设置切片中的值。
func rotateSlice(a interface{}, i int) {
v := reflect.ValueOf(a).Elem()
x, b := v.Slice(0, i), v.Slice(i, v.Len())
v.Set(reflect.AppendSlice(b, x))
}
使用指向切片的指针来调用该函数:
a := []string{"a", "b", "c", "d"}
rotateSlice(&a, 2)
英文:
Eliminate the use of the reflect package in Go 1.18 and later by using generics:
func rotateSlice[T any](a []T, i int) []T {
x, b := a[:i], a[i:]
return append(b, x...)
}
Call it like this: x = rotateSlice(x, 2)
Here's now to implement rotate using the reflect package.
Use Value.Set to set the value in the slice.
func rotateSlice(a interface{}, i int) {
v := reflect.ValueOf(a).Elem()
x, b := v.Slice(0, i), v.Slice(i, v.Len())
v.Set(reflect.AppendSlice(b, x))
}
Call the function with a pointer to a slice:
a := []string{"a", "b", "c", "d"}
roateSlice(&a, 2)
答案2
得分: 1
a
是一个interface{}
而不是指针,所以你不能对其进行解引用操作。即使你有一个指向切片的指针,你也不能将reflect.AppendSlice
的结果赋值给它,因为它返回的是reflect.Value
类型。你需要通过Value.Set
方法来设置值。
func rotateSlice(a interface{}, i int) {
v := reflect.ValueOf(a).Elem()
x, b := v.Slice(0, i), v.Slice(i, v.Len())
v.Set(reflect.AppendSlice(b, x))
}
你可以在这里查看示例代码:https://play.golang.org/p/JCF8jsRJ_O
英文:
a
is an interface{}
not a pointer, so you can't dereference it. Even if you have a pointer to a slice, you can't assigned the result ofreflect.AppendSlice
, because it returns the type reflect.Value
. You need to set the value via Value.Set
.
https://play.golang.org/p/JCF8jsRJ_O
func rotateSlice(a interface{}, i int) {
v := reflect.ValueOf(a).Elem()
x, b := v.Slice(0, i), v.Slice(i, v.Len())
v.Set(reflect.AppendSlice(b, x))
}
通过集体智慧和协作来改善编程学习和解决问题的方式。致力于成为全球开发者共同参与的知识库,让每个人都能够通过互相帮助和分享经验来进步。
评论