doushui3061 2017-05-25 11:28
浏览 62
已采纳

如何在不使用sync.WaitGroup的情况下防止死锁?

concurrent.go:

package main

import (
    "fmt"
    "sync"
)

// JOBS represents the number of jobs workers do
const JOBS = 2

// WORKERS represents the number of workers
const WORKERS = 5

func work(in <-chan int, out chan<- int, wg *sync.WaitGroup) {
    for n := range in {
        out <- n * n
    }
    wg.Done()
}

var wg sync.WaitGroup

func main() {
    in := make(chan int, JOBS)
    out := make(chan int, JOBS)

    for w := 1; w <= WORKERS; w++ {
        wg.Add(1)
        go work(in, out, &wg)
    }

    for j := 1; j <= JOBS; j++ {
        in <- j
    }
    close(in)

    wg.Wait()
    close(out)
    for r := range out {
        fmt.Println("result:", r)
    }

    // This is a solution but I want to do it with `range out`
    // and also without WaitGroups
    // for r := 1; r <= JOBS; r++ {
    //  fmt.Println("result:", <-out)
    // }
}

Example is here on goplay.

  • 写回答

2条回答 默认 最新

  • doujie3888 2017-05-25 14:25
    关注

    This is a proof of example syncing without waitgroup.

    Example in the Go playground

    package main
    
    import (
        "fmt"
    )
    
    // number of jobs workers do
    const JOBS = 10
    
    // number of workers
    const WORKERS = 2
    
    func work(in <-chan int, out chan<- int, done chan<- bool) {
        for n := range in {
            out <- n * n
        }
        done <- true
    }
    
    func main() {
        in := make(chan int, JOBS)
        out := make(chan int, JOBS)
        done := make(chan bool, WORKERS)
    
        // launch workers
        for w := 1; w <= WORKERS; w++ {
            go work(in, out, done)
        }
    
        // give jobs to workers
        for j := 1; j <= JOBS; j++ {
            in <- j
        }
        close(in)
    
        // list the results
        go func() {
            i := 0
            for r := range out {
                fmt.Println("result:", r)
    
                // when all jobs completed mark as done
                if i++; i == JOBS {
                    done <- true
                }
            }
        }()
    
        // wait for all goroutines to keep up
        // WORKERS + RESULT go routines
        for i := 0; i < WORKERS + 1; i++ {
            <- done
        }
    
        // prevent leaking chans
        close(out)
    }
    
    本回答被题主选为最佳回答 , 对您是否有帮助呢?
    评论
查看更多回答(1条)

报告相同问题?

悬赏问题

  • ¥15 matlab生成电测深三层曲线模型代码
  • ¥50 随机森林与房贷信用风险模型
  • ¥50 buildozer打包kivy app失败
  • ¥30 在vs2022里运行python代码
  • ¥15 不同尺寸货物如何寻找合适的包装箱型谱
  • ¥15 求解 yolo算法问题
  • ¥15 虚拟机打包apk出现错误
  • ¥15 用visual studi code完成html页面
  • ¥15 聚类分析或者python进行数据分析
  • ¥15 三菱伺服电机按启动按钮有使能但不动作