繁体   English   中英

指针接收器与值的方法,值和指针之间的转换

[英]Method with pointer receiver vs value , conversion between value and pointer

作为学习指针与值接收器的一部分,我提到了: https://gobyexample.com/methods

// This `area` method has a _receiver type_ of `*rect`.
func (r *rect) area() int {
    return r.width * r.height
}

// Methods can be defined for either pointer or value
// receiver types. Here's an example of a value receiver.
func (r rect) perim() int {
    return 2*r.width + 2*r.height
}

func main() {
    r := rect{width: 10, height: 5}

    // Here we call the 2 methods defined for our struct.
    fmt.Println("area: ", r.area())
    fmt.Println("perim:", r.perim())

    // Go automatically handles conversion between values
    // and pointers for method calls. You may want to use
    // a pointer receiver type to avoid copying on method
    // calls or to allow the method to mutate the
    // receiving struct.
    rp := &r
    fmt.Println("area: ", rp.area())
    fmt.Println("perim:", rp.perim())
}

我不明白-->

rp := &r   
rp is a pointer or address of r

为什么结果:

rp.area()  is identical to r.area() 
rp.perim()  is identical to r.perim()

指针:它们是 memory 中 var 的地址。

function area() 需要一个指针接收器。 所以这很清楚 rp.area() (因为 rp 是 r 的指针或地址)

但是为什么这个 r.area()? r 不是指针而是值

同样 perim 需要一个我们使用指针作为接收者的值? rp.perim()

还有这意味着什么:

您可能希望使用指针接收器类型来避免复制方法调用或允许方法改变接收结构。

to avoid copying on method calls or to allow the method to mutate the receiving struct.

您需要了解指针是什么才能了解这里发生了什么。 指针包含另一个变量的地址。

这两种接收器的不同之处在于,一种(指针)需要一个地址,而另一种(值)需要一个非地址。

现在,回答你的第一个问题:“为什么结果是一样的?”

首先, rp是指向r的指针。 这意味着rp中包含的是r的地址。 所以rrp最终都引用相同的结构( r直接包含它并且rp中的地址指向它)。 所以最后它是相同的结构。

此外, rrp都可以与指针和值接收器一起使用的原因是:Go 在调用perim()时自动获取rp中包含的地址(作为值接收器需要非地址),它在调用area()时自动获取r的地址以供传递(作为指针接收器需要地址)。

回答你的第二个问题:“这是什么意思......?”

要理解这一点,您需要知道 Go 中的所有函数都使用按值传递。 这意味着当您将具有许多字段的结构传递给 function 时,整个结构及其所有字段将被复制到一个新变量中以在 function 中使用。 但是,如果您传递一个指针(具有许多字段的结构的地址),则只会将该地址复制到要在 function 内部使用的变量中——复制要少得多。

暂无
暂无

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

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