范围的奇怪行为

考虑以下最小示例:


package main


import "fmt"


type runner interface {

    s1(int)

    s2(int)

}


type test struct {

    x1 []int

    x2 []int

}


func (t test) s1(v int) {

    t.x1 = append(t.x1, v)

    t.s2(v)

}


func (t test) s2(v int) {

    t.x2[v] = v

}



func main() {

    t := test{

        x1: make([]int, 0),

        x2: make([]int, 10)}


    for i := 0; i < 10; i++ {

        t.s1(i)

    }


    fmt.Println(t)

}

现在如果你运行它,你将得到如下结果:


{[] [0 1 2 3 4 5 6 7 8 9]}

这意味着该x1数组永远不会被填充。或者实际上,它是,但每次s1函数退出时都会重置。s2将项目放入预定义的数组中效果很好。


有谁知道这里到底发生了什么?是因为数组修改的范围吗?这似乎有点违反直觉。


PS 我确实明白 x1 是一个切片,其中 x2 是一个实际的预定义数组。我自己的理论是,如果您使用“切片”,它们只能在特定范围内更改,而不能在其他任何地方更改。



慕尼黑8549860
浏览 90回答 1
1回答

婷婷同学_

值接收者制作类型的副本并将其传递给函数。只需将其设置为指针即可:func (t *test) s1(v int) {&nbsp; &nbsp; t.x1 = append(t.x1, v)&nbsp; &nbsp; t.s2(v)}输出:&{[0 1 2 3 4 5 6 7 8 9] [0 1 2 3 4 5 6 7 8 9]}代码:package mainimport "fmt"type runner interface {&nbsp; &nbsp; s1(int)&nbsp; &nbsp; s2(int)}type test struct {&nbsp; &nbsp; x1 []int&nbsp; &nbsp; x2 []int}func (t *test) s1(v int) {&nbsp; &nbsp; t.x1 = append(t.x1, v)&nbsp; &nbsp; t.s2(v)}func (t test) s2(v int) {&nbsp; &nbsp; t.x2[v] = v}func main() {&nbsp; &nbsp; t := &test{&nbsp; &nbsp; &nbsp; &nbsp; x1: make([]int, 0),&nbsp; &nbsp; &nbsp; &nbsp; x2: make([]int, 10)}&nbsp; &nbsp; for i := 0; i < 10; i++ {&nbsp; &nbsp; &nbsp; &nbsp; t.s1(i)&nbsp; &nbsp; }&nbsp; &nbsp; fmt.Println(t)}
打开App,查看更多内容
随时随地看视频慕课网APP

相关分类

Go