pointers - 从作为接口(interface)传递的指针连接 slice

标签 pointers go reflection slice

我正在为一个特定的 API 开发一个客户端,我构建了几个结构(每个路由一个)。
API 适用于页面,因此我有 getter 返回结构的 slice 。这是通过一个通用函数完成的,该函数采用一个接口(interface),该接口(interface)应该是指向所需结构的一部分的指针,因此我可以使用 json 包中的 Unmarshal

我面临的问题是我想在一个请求中获取所有页面,但为了做到这一点,我需要连接多个 slice 。

我尝试使用 reflect 来做到这一点,但我只能设法创建一个新 slice ,而不会实际改变我的接口(interface)指向的值。

这是我的部分代码:

func concatenateSlice(dst, src interface{})(){
    dstValue := reflect.ValueOf(dst)
    srcValue := reflect.ValueOf(src)
    if srcValue.Type() != dstValue.Type(){
        return
    }
    switch srcValue.Kind(){
    case reflect.Ptr, reflect.Slice:
        dstValuePoint := reflect.Indirect(dstValue)
        srcValuePoint := reflect.Indirect(srcValue)
        reflect.Copy(dstValuePoint, reflect.AppendSlice(dstValuePoint, srcValuePoint))
    }
}

对于草率的帖子,我很抱歉,这是我第一次使用 stackoverflow。

最佳答案

你不应该使用 reflect.Copy()复制结果 slice (追加后),因为目标没有足够的空间。 reflect.AppendSlice()不会更改 dst 指向的 slice ,它会在需要时分配一个新 slice ,并返回新 slice (更准确地说是持有它的 reflect.Value)。

您应该做的是将 reflect.AppendSlice() 返回的 slice 设置为 dst 指向的值,只需使用 Value.Set()方法。需要注意的一件事是您不是设置 slice 指针而是设置 slice ,因此首先调用例如Value.Elem()在调用 Set() 之前。

看这个例子:

func concatenateSlice(dst, src interface{}) {
    dv := reflect.ValueOf(dst)
    sv := reflect.ValueOf(src)
    if dv.Type() != sv.Type() {
        return
    }

    dv2 := reflect.AppendSlice(dv.Elem(), sv.Elem())
    dv.Elem().Set(dv2)
}

测试它:

dst := []int{1, 2}
src := []int{3, 4}

concatenateSlice(&dst, &src)

fmt.Println(dst)

输出(在 Go Playground 上尝试):

[1 2 3 4]

关于pointers - 从作为接口(interface)传递的指针连接 slice ,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/51628655/

相关文章:

go - 如何构建 Kubernetes 以便将调试信息包含在可执行文件中?

java - 通过反射Java获取对象中的字段及其值

java - 使用 GSON 避免在 json 映射中使用原始数据类型默认值

java - 如何找出 EnumMap 中使用的枚举?

c++ - 我是否需要使用继承对象(相对于基础对象)来覆盖我的虚函数?

c++ - 从类中提供指向私有(private)成员的指针

c++ - 通过 volatile 引用/指针访问声明的非 volatile 对象是否赋予所述访问 volatile 规则?

C# 字符* 到字符串

excel - Go中未提供工作表/节名称时如何从XLS文件读取所有行

go - TLS session 恢复