亚洲在线久爱草,狠狠天天香蕉网,天天搞日日干久草,伊人亚洲日本欧美

為了賬號安全,請及時綁定郵箱和手機立即綁定
已解決430363個問題,去搜搜看,總會有你想問的

未從戈魯廷獲得預期輸出

未從戈魯廷獲得預期輸出

Go
慕標5832272 2022-09-19 14:59:05
我在(https://www.geeksforgeeks.org/channel-in-golang/)上讀到:“在信道中,發送和接收操作阻塞,直到另一端默認未就緒。它允許戈魯廷在沒有顯式鎖或條件變量的情況下相互同步。為了測試上面的語句,我編寫了一個示例程序,如下所述:程序:package mainimport (    "fmt"    "sync"    "time")func myFunc(ch chan int) {    fmt.Println("Inside goroutine:: myFunc()")    fmt.Println(10 + <-ch) //<-- According to rule, control will be blocked here until 'ch' sends some data so that it will be received in our myFunc() go routine.}func main() {    fmt.Println("Start Main method")    // Creating a channel    ch := make(chan int)    go myFunc(ch) //<-- This go routine started in a new thread    time.Sleep(2 * time.Second) //<--- introduced a Sleep of 2 seconds to ensure that myFunc() go routine executes before main thread    ch <- 10    fmt.Println("End Main method")}我期待下面的輸出:Start Main methodInside goroutine:: myFunc()20End Main method但是,實際接收的輸出是:Start Main methodInside goroutine:: myFunc()End Main method為什么通過通道發送的值沒有打印出來?我認為,這是因為主線程首先完成了它的執行,因此,所有其他goroutine也終止了。如果是這樣的話,那么,為什么規則說 - 它允許goroutine在沒有顯式鎖或條件變量的情況下相互同步。因為,為了獲得預期的輸出,我必須使用告訴主線程等待另一個 goroutine 完成。這不是違反了上述規則,因為我以等待組的形式使用鎖?sync.WaitGroupPS:我正在學習戈朗。所以,如果我完全理解了這個概念,請原諒。
查看完整描述

4 回答

?
江戶川亂折騰

TA貢獻1851條經驗 獲得超5個贊

試試這個,使用你的代碼作為基礎


package main


import (

    "fmt"

    "time"

)


func myFunc(ch chan int, done chan struct{}) {

    defer close(done) // channel will be closed in the function exit phase

    fmt.Println("Inside goroutine:: myFunc()")

    fmt.Println(10 + <-ch) //<-- According to rule, control will be blocked here until 'ch' sends some data so that it will be received in our myFunc() go routine.

}

func main() {


    fmt.Println("Start Main method")

    // Creating a channel

    ch := make(chan int)

    done := make(chan struct{}) // signal channel


    go myFunc(ch, done) //<-- This go routine started in a new thread


    time.Sleep(2 * time.Second) //<--- introduced a Sleep of 2 seconds to ensure that myFunc() go routine executes before main thread

    ch <- 10

    <-done // waiting for function complete

    fmt.Println("End Main method")

}

或者使用雅羅斯瓦夫的建議。


查看完整回答
反對 回復 2022-09-19
?
BIG陽

TA貢獻1859條經驗 獲得超6個贊

主戈魯廷在戈魯廷能夠打印輸出之前就已存在。下面是一個實現,它確保戈魯廷在主戈魯丁退出之前完成。myFuncmyFunc


package main


import (

    "fmt"

    "sync"

    "time"

)


func myFunc(ch chan int, wg *sync.WaitGroup) {

    defer wg.Done()

    fmt.Println("Inside goroutine:: myFunc()")

    fmt.Println(10 + <-ch) //<-- According to rule, control will be blocked here until 'ch' sends some data so that it will be received in our myFunc() go routine.

}

func main() {


    fmt.Println("Start Main method")

    // Creating a channel

    ch := make(chan int)

    wg := sync.WaitGroup{}

    wg.Add(1)

    go myFunc(ch, &wg) //<-- This go routine started in a new thread


    time.Sleep(2 * time.Second) //<--- introduced a Sleep of 2 seconds to ensure that myFunc() go routine executes before main thread

    ch <- 10

    wg.Wait()

    fmt.Println("End Main method")

}

此處的通道用于同步,其工作方式與文檔中的說明相同。這并不意味著從代碼中的這一點開始的代碼將以相同的速度執行。這只意味著如果戈魯廷沒有從頻道讀取,主戈魯廷將不會繼續。并將等待主戈魯丁將數據推送到通道。發生這種情況后,兩個哥律特將繼續獨立執行。myFuncmyFunc


查看完整回答
反對 回復 2022-09-19
?
藍山帝景

TA貢獻1843條經驗 獲得超7個贊

因為去太快了...https://play.golang.org/p/LNyDAA3mGYY

發送到頻道調度程序后,速度不快...和程序存在。我為調度程序引入了一個額外的上下文切換器來顯示效果。


查看完整回答
反對 回復 2022-09-19
?
長風秋雁

TA貢獻1757條經驗 獲得超7個贊

是的,你是對的


我認為,這是因為主線程首先完成了它的執行,因此,所有其他goroutine也終止了。


如果您檢查上述程序的執行情況。休眠狀態是在主線程寫入通道之前?,F在即使哪個 goroutine() 將有 CPU 時間是完全任意的,但在上述情況下,如果休眠在邏輯之前。 將被阻止,因為 中沒有數據mainexplicit sleepmyFuncch


在這里,我對上面的代碼進行了輕微的更改,以便在將數據寫入 Channel 后進行睡眠。它提供預期的輸出,不使用 或 。mainwaitgroupquit channels


package main


import (

    "fmt"

    "time"

)


func myFunc(ch chan int) {

    fmt.Println("Inside goroutine:: myFunc()")

    fmt.Println(10 + <-ch) //<-- According to rule, control will be blocked here until 'ch' sends some data so that it will be received in our myFunc() go routine.

}

func main() {


    fmt.Println("Start Main method")

    // Creating a channel

    ch := make(chan int)


    go myFunc(ch) //<-- This go routine started in a new thread


   

    ch <- 10

    

    time.Sleep(2 * time.Second) //<--- introduced a Sleep of 2 seconds to ensure that myFunc() go routine executes before main thread



    fmt.Println("End Main method")

}


查看完整回答
反對 回復 2022-09-19
  • 4 回答
  • 0 關注
  • 108 瀏覽
慕課專欄
更多

添加回答

舉報

0/150
提交
取消
微信客服

購課補貼
聯系客服咨詢優惠詳情

幫助反饋 APP下載

慕課網APP
您的移動學習伙伴

公眾號

掃描二維碼
關注慕課網微信公眾號