首頁 >後端開發 >Golang >對於同一結構體,Golang 在 for 迴圈中 defer 的行為有所不同

對於同一結構體,Golang 在 for 迴圈中 defer 的行為有所不同

WBOY
WBOY轉載
2024-02-06 09:30:111012瀏覽

对于同一结构体,Golang 在 for 循环中 defer 的行为有所不同

問題內容

我寫了以下 golang 程式碼並執行了它。

type test struct {
    name string
}

func (t test) hello() {
    fmt.printf("hello, %s\n", t.name)
}

func (t *test) hello2() {
    fmt.printf("pointer: %s\n", t.name)
}

func runt(t test) {
    t.hello()
}

func main() {
    mapt := []test{
        {name: "a"},
        {name: "b"},
        {name: "c"},
    }

    for _, t := range mapt {
        defer t.hello()
        defer t.hello2()
    }
}

輸出:

pointer: C
Hello, C
pointer: C
Hello, B
pointer: C
Hello, A

我的理解是,指標 t 在 3 個循環後將指向“c”,因此三個 3“c”用於“hello2”輸出。然而,延遲“hello”函數呼叫的行為非常奇怪。看起來它正在保留它所指向的位置。 (t test) 如何影響這個?

我很好奇golang將其編譯成什麼。非常感謝!


正確答案


在 for 迴圈內,defer 語句的參數是一個閉包。閉包捕獲循環變數 t

對於使用值接收器的調用,閉包包含 t 的副本。對於使用指標接收器的調用,閉包包含一個指向 t 的指標。

循環變數在每次迭代時都會被重寫(此行為將在該語言的更高版本中更改)。因此,值接收器閉包捕獲每個值,而指針接收器閉包僅捕獲指針,因此,在運行時,它們使用該指針的最新值。

以上是對於同一結構體,Golang 在 for 迴圈中 defer 的行為有所不同的詳細內容。更多資訊請關注PHP中文網其他相關文章!

陳述:
本文轉載於:stackoverflow.com。如有侵權,請聯絡admin@php.cn刪除