sync.WaitGroup的使用以及坑


all goroutines are asleep - deadlock 

簡單使用:

package main import ( "sync" ) type httpPkg struct{} func (httpPkg) Get(url string) {} var http httpPkg func main() { var wg sync.WaitGroup var urls = []string{ "http://www.golang.org/", "http://www.google.com/", "http://www.somestupidname.com/", } for _, url := range urls { // Increment the WaitGroup counter. wg.Add(1) // Launch a goroutine to fetch the URL. go func(url string) { // Decrement the counter when the goroutine completes. defer wg.Done() // Fetch the URL. http.Get(url) }(url) } // Wait for all HTTP fetches to complete. wg.Wait() } 

這是golang官網上的例子

跟java的CountdownLatch差不多,也是阻塞等待所有任務完成之后再繼續執行。

簡單使用就是在創建一個任務的時候wg.Add(1), 任務完成的時候使用wg.Done()來將任務減一。使用wg.Wait()來阻塞等待所有任務完成。

然后我就寫了一個例子:

func main() {
    var wg sync.WaitGroup
    ch := make(chan int, 1000)
    for i := 0; i < 1000; i++ {
        wg.Add(1)
        go doSomething(i, wg, ch)
    }
    wg.Wait()
    fmt.Println("all done")
    for i := 0; i < 1000; i++ {
        dd := <-ch
        fmt.Println("from ch:"+strconv.Itoa(dd))
    }
}

func doSomething(index int, wg  sync.WaitGroup, ch chan int) {
    defer wg.Done()
    fmt.Println("start done:" + strconv.Itoa(index))
    //time.Sleep(20 * time.Millisecond)
    ch <- index
}

然后就報錯了:

fatal error: all goroutines are asleep - deadlock!
goroutine 1 [semacquire]:
sync.runtime_Semacquire(0xc42001608c)
    /usr/local/Cellar/go/1.10.3/libexec/src/runtime/sema.go:56 +0x39
sync.(*WaitGroup).Wait(0xc420016080)
    /usr/local/Cellar/go/1.10.3/libexec/src/sync/waitgroup.go:129 +0x72
main.main()
    /Users/taoli/go/src/github.com/c60/cai/tx_gorutine.go:16 +0xea

怎么回事,他說死鎖了。
原來這是說,所有的協程都運行完了,你這邊還在等待。

什么原因導致的呢?
原來是golang里如果方法傳遞的不是地址,那么就會做一個拷貝,所以這里調用的wg根本就不是一個對象。

傳遞的地方傳遞地址就可以了:

go doSomething(i, &wg, ch) func doSomething(index int, wg *sync.WaitGroup, ch chan int) {


作者:ironman_
鏈接:https://www.jianshu.com/p/4c2c80076094
來源:簡書
著作權歸作者所有。商業轉載請聯系作者獲得授權,非商業轉載請注明出處。


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM