Methods 为什么不';通过方法对结构所做的更改是否持久?

Methods 为什么不';通过方法对结构所做的更改是否持久?,methods,struct,go,Methods,Struct,Go,我试图理解为什么以下测试代码不能按预期工作: package main import ( "fmt" "strings" ) type Test struct { someStrings []string } func (this Test) AddString(s string) { this.someStrings = append(this.someStrings, s) this.Count() // will print "1" } fu

我试图理解为什么以下测试代码不能按预期工作:

package main

import (
    "fmt"
    "strings"
)

type Test struct {
    someStrings []string
}

func (this Test) AddString(s string) {
    this.someStrings = append(this.someStrings, s)
    this.Count() // will print "1"
}

func (this Test) Count() {
    fmt.Println(len(this.someStrings))
}

func main() {
    var test Test
    test.AddString("testing")
    test.Count() // will print "0"
}
这将打印:

"1"
"0"
这意味着
someStrings
显然被修改了。。。但事实并非如此


有人知道可能是什么问题吗?

AddString方法使用的是值(复制)接收器。修改的是副本,不是原件。必须使用指针接收器来改变原始实体:

package main

import (
        "fmt"
)

type Test struct {
        someStrings []string
}

func (t *Test) AddString(s string) {
        t.someStrings = append(t.someStrings, s)
        t.Count() // will print "1"
}

func (t Test) Count() {
        fmt.Println(len(t.someStrings))
}

func main() {
        var test Test
        test.AddString("testing")
        test.Count() // will print "0"
}


输出

1
1

函数是在对象本身上定义的,而不是指向对象的指针

func (this Test) AddString(s string) {
    this.someStrings = append(this.someStrings, s)
    this.Count() // will print "1"
}
上述功能是在具体数据上定义的。这意味着调用函数时,
This
的值作为数据的副本传入。因此,您对
这个
所做的任何变异都是在副本上完成的(在本例中,变异是更改“someStrings”指向的指针。我们可以重写在测试指针上定义的与jnml相同的函数:

func (this *Test) AddString(s string) {
    this.someStrings = append(this.someStrings, s)
    this.Count() // will print "1"
}

如您所见,函数定义是
(此*测试)
,而不是
(此测试)
。这意味着变量
This
通过引用传递,发生的任何突变都是在原始对象上执行的突变。

Go将通过值传递所有内容。这包括函数参数、返回值以及在切片、贴图或通道上迭代时的值

若要添加到@noj的答案,若您将接收器切换到*测试类型,go将自动使用指针