简体   繁体   English

在另一个 function 中更改 golang 切片

[英]Change golang slice in another function

I have a slice, if i remove one element from it directly in a main function the length of slice would be cut by one.我有一个切片,如果我直接在主 function 中从中删除一个元素,切片的长度将减一。 But do the remove in another function and called it in main, the length of the slice is still keep origin.但是在另一个 function 中删除并在 main 中调用它,切片的长度仍然保持原点。 Who can explain it for me?谁能给我解释一下? Thanks!谢谢!

package main

import "fmt"

func main() {
    a := []int{1, 2, 3, 4}
    i := 0

    //copy(a[i:], a[i+1:])
    //a[len(a)-1] = 0
    //a = a[:len(a)-1]
    //fmt.Println(a)    //outputs: [2 3 4], this is correct

    f(a, i)
    fmt.Println(a) //outputs: [2 3 4 0], this is wrong!
}

func f(a []int, i int) {
    copy(a[i:], a[i+1:])
    a[len(a)-1] = 0
    a = a[:len(a)-1]
    fmt.Println(a) //outputs: [2 3 4], here still correct
}

Go Playground Link Go 游乐场链接

The slice is passed by value, so changing it in your function f won't change it in function main .切片是按值传递的,因此在 function f中更改它不会在 function main中更改它。 You can pass by pointer, like this:您可以通过指针传递,如下所示:

package main

import "fmt"

func main() {
    a := []int{1, 2, 3, 4}
    i := 0

    f(&a, i)
    fmt.Println(a)    //outputs: [2 3 4], correct
}

func f(a *[]int, i int) {
    b := *a
    copy(b[i:], b[i+1:])
    // The following line seems pointless, but ok...
    b[len(b)-1] = 0
    b = b[:len(b)-1]
    fmt.Println(b)    //outputs: [2 3 4], here still correct
    *a = b
}

Go Playground Go 游乐场

As suggested by @zerkms in the comments, you could also return the new slice, avoiding the use of pointers:正如@zerkms 在评论中所建议的那样,您还可以返回新切片,避免使用指针:

package main

import "fmt"

func main() {
    a := []int{1, 2, 3, 4}
    i := 0

    a = f(a, i)
    fmt.Println(a)
}

func f(a []int, i int) []int {
    copy(a[i:], a[i+1:])
    // The following line seems pointless, but ok...
    a[len(a)-1] = 0
    a = a[:len(a)-1]
    fmt.Println(a)     //outputs: [2 3 4], here still correct
    return a
}

Not providing new solution, just trying to explain why your program is behaving the way you asked:没有提供新的解决方案,只是试图解释为什么您的程序会按照您的要求行事:

Let us try to understand first how the built in function 'copy' works Ref: [ https://golang.org/pkg/builtin/#copy]让我们首先尝试了解内置 function 'copy' 是如何工作的 Ref: [ https://golang.org/pkg/builtin/#copy]

func copy(dst, src []Type) int

The copy built-in function copies elements from a source slice into a destination slice.复制内置 function 将元素从源切片复制到目标切片。 (As a special case, it also will copy bytes from a string to a slice of bytes.) The source and destination may overlap. (作为一种特殊情况,它还将字节从字符串复制到字节片。)源和目标可能重叠。 Copy returns the number of elements copied, which will be the minimum of len(src) and len(dst). Copy 返回复制的元素数量,它将是 len(src) 和 len(dst) 的最小值。

Two things: 1. First comment the line: //a[len(a)-1] = 0两件事:1.首先注释该行://a[len(a)-1] = 0

  1. Second: As you are using the same array ie as source and destination you are getting [2,3,4,4] as output as the destination array is {1,2,3,4} which got overwritten to {2,3,4,4(which is already present)} you can try with different array's to make it more clear to you第二:当您使用相同的数组,即作为源和目标时,您将得到 [2,3,4,4] 作为 output 因为目标数组是 {1,2,3,4} 被覆盖到 {2,3 ,4,4(已经存在)}您可以尝试使用不同的数组以使您更清楚

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

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