Rumah  >  Artikel  >  pembangunan bahagian belakang  >  Melepasi penuding untuk pergi menunda fungsi tidak berfungsi

Melepasi penuding untuk pergi menunda fungsi tidak berfungsi

WBOY
WBOYke hadapan
2024-02-13 12:24:09611semak imbas

将指针传递给 go defer 函数不起作用

Dalam pengaturcaraan PHP, penuding mungkin tidak berfungsi apabila dihantar ke fungsi go defer. Penunjuk dalam PHP digunakan untuk menyimpan alamat memori pembolehubah Dengan menghantar penunjuk, nilai pembolehubah asal boleh diubah suai di dalam fungsi. Walau bagaimanapun, apabila menghantar penunjuk ke fungsi go defer, kadangkala berlaku pembolehubah asal tidak boleh diubah suai. Ini mungkin kerana fungsi go defer mencipta Goroutine baharu apabila dilaksanakan, dan penuding mungkin menghala ke ruang memori yang berbeza, mengakibatkan kegagalan untuk mengubah suai nilai pembolehubah dengan betul. Oleh itu, dalam pengaturcaraan PHP, penunjuk harus dihantar untuk menangguhkan fungsi dengan berhati-hati untuk mengelakkan masalah yang tidak dijangka.

Kandungan soalan

Dalam kod saya, saya cuba menggunakan numaddr untuk merekodkan pertukaran nombor selepas penyata penangguhan

func deferrun() {
    num := 1
    numaddr := &num
    defer fmt.printf("num is %d", *numaddr)
    num = 2
    return
}

func main() {
    deferrun()
}

Tetapi saya mendapat nilai num 是 1 而不是 2,为什么 defer 函数使用 *numaddr dan bukannya alamat?

Lepastu saya akan cuba kaedah lain

func deferRun() {
    num := 1
    numAddr := &num
    defer func(intAddr *int){
        fmt.Printf("num is %d", *numAddr)
    }(numAddr)
    
    num = 2
    fmt.Println("num is", *numAddr)
    return
}

func main() {
    deferRun()
}

Kali ini ia berfungsi, saya dapat num 是 2,所以我想也许 defer fmt.printf(something) Rentetan disimpan serta-merta apabila mengisytiharkannya dan numaddr tidak digunakan apabila fungsi tangguh sebenarnya berjalan?

Penyelesaian

Persoalan yang menarik. Untuk menjawab soalan ini, anda mesti mengetahui peraturan, seperti tutorial go ini https://go.dev/tour/flowcontrol/12

延迟调用的参数会立即计算,但直到周围函数返回时才会执行函数调用。.

Contoh 1: Beritahu fungsi tangguh untuk mencetak nilai yang terletak di alamat memori yang ditentukan.

func deferrun() {
    num := 1
    numaddr := &num //address of variable num in stack memory, 0xc000076f38 for example
    defer func(intaddr *int){
        fmt.printf("num is %d", *numaddr)
    }(numaddr) //hey go, when the surrounding function returns, print the value located in this address (numaddr=0xc000076f38)
    num = 2 //now the value located in address 0xc000076f38 is 2
    return  
}

Keluaran akan menjadi 2.

Contoh 2: Beritahu fungsi tangguh untuk mencetak nilai yang ditentukan.

func deferRun() {
    num := 1
    numAddr := &num //address of variable num in stack memory, 0xc000076f38 for example
    defer fmt.Printf("num is %d", *numAddr) //Hey Go, when the surrounding function returns, print the this value *numAddr (*numAddr is 1 for now)
    num = 2 //Now the value located in address 0xc000076f38 is 2 but you told the defer function to print 1 before
    return  
}

Hasilnya ialah 1.

Atas ialah kandungan terperinci Melepasi penuding untuk pergi menunda fungsi tidak berfungsi. Untuk maklumat lanjut, sila ikut artikel berkaitan lain di laman web China PHP!

Kenyataan:
Artikel ini dikembalikan pada:stackoverflow.com. Jika ada pelanggaran, sila hubungi admin@php.cn Padam