go tour --方法值接收器和指標接收器區別
阿新 • • 發佈:2020-07-17
有兩個理由使用指標接收器
- 第一個是為了讓方法可以修改它的接收器指向的值。
- 第二種方法是避免在每次方法呼叫時複製值。例如,如果接收方是一個大的結構體,這可能會更有效率。
通常,給定型別上的所有方法都應該具有值或指標接收器,但不能兩者混合。(我們將在接下來的幾頁中看到原因。)
介面
介面是定義的一組方法簽名。
實現介面必須啊實現介面的所有方法。
實現介面必須要值接收器方法。
在底層,一個介面值可以被認為是一個值和具體型別的元組
(value, type)
呼叫介面值上的方法將在其底層型別上執行同名方法。
如果介面內部的具體值本身是nil,該方法將用nil接收器呼叫。(但還是會呼叫方法,因為有型別,可以在方法內通過判斷接收器為nil 來避免空指標錯誤)
package main import "fmt" type I interface { M() } type T struct { S string } func (t *T) M() { if t == nil { fmt.Println("<nil>") return } fmt.Println(t.S) } func main() { var i I var t *T i = t describe(i) i.M() i = &T{"hello"} describe(i) i.M() } func describe(i I) { fmt.Printf("(%v, %T)\n", i, i) }
注意,持有nil具體值的介面值本身是非nil的。
nil介面值既不包含值也不包含具體型別。
在nil介面上呼叫方法是一個執行時錯誤,因為在介面元組中沒有型別來指示要呼叫哪個具體方法。
package main
import "fmt"
type I interface {
M()
}
func main() {
var i I
describe(i)
i.M()
}
func describe(i I) {
fmt.Printf("(%v, %T)\n", i, i)
}
(<nil>, <nil>) panic: runtime error: invalid memory address or nil pointer dereference [signal 0xc0000005 code=0x0 addr=0x0 pc=0x49c106] goroutine 1 [running]: main.main()