问答

go group并发执行

作者:admin 2021-04-30 我要评论

假如我有100个任务需要执行,但是我只想同时并发40个,因此我想先并发执行前40个,等这40个都执行完了之后在执行40个,等这40个执行完后再执行最后的20个。想到...

在说正事之前,我要推荐一个福利:你还在原价购买阿里云、腾讯云、华为云服务器吗?那太亏啦!来这里,新购、升级、续费都打折,能够为您省60%的钱呢!2核4G企业级云服务器低至69元/年,点击进去看看吧>>>)

假如我有100个任务需要执行,但是我只想同时并发40个,因此我想先并发执行前40个,等这40个都执行完了之后在执行40个,等这40个执行完后再执行最后的20个。想到这我就想到了搞一个“协程池”,不知道go有没有类似的开源的协程池项目有?或者有不用协程池也能解决的方案?

###
package main

import (
    "fmt"
    "sync"
)

func main() {
    max := 40    // 最大协程数量限制
    tasks := 100 // 任务数量
    wg := sync.WaitGroup{}
    ch := make(chan struct{}, max)
    for i := 0; i < tasks; i++ {
        wg.Add(1)        // 添加计数
        ch <- struct{}{} // 写一个标记到 chan,chan缓存满时会阻塞
        go func(j int) {
            defer func() {
                wg.Done() // 将计数减1
                <-ch      // 读取chan
            }()

            fmt.Println(j)

        }(i)
    }
    wg.Wait() // 等待加入的协程全部完成
    fmt.Println("done...")
}
 
###

可以用channel + waitgroup, 大概思路如下

// 每轮任务个数
const Speed = 40
// 任务总数
const total = 100
// 任务
tasks := make([]interface{}, 0)
taskChan := make(chan interface{}, Speed)
// 已执行任务个数
executedNum := 0
wg := &sync.WaitGroup{}
go func() {
   for {
      num := total - executedNum
      if num <= 0{
        return
      }
      if num > Speed {
         executedNum += Speed
         num = Speed
      }
      wg.Add(num)
      for i := 0; i < num; i++ {
         task := <-taskChan
         go func(task interface{}) {
            defer wg.Done()
            task.Do()
         }(task)
      }
      wg.Wait()
   }
}()
for i := 0; i < len(tasks); i++ {
   taskChan <- tasks[i]
}

版权声明:本文转载自网络,遵循 CC 4.0 BY-SA 版权协议,转载请附上原文出处链接和本声明。本站转载出于传播更多优秀技术知识之目的,如有侵权请联系QQ/微信:153890879删除

相关文章
  • 从github上clone代码后文件不显示绿勾

    从github上clone代码后文件不显示绿勾

  • 父组件中循环子组件,子组件$emit触发A

    父组件中循环子组件,子组件$emit触发A

  • 在实现bind函数时,源码中的instanceof

    在实现bind函数时,源码中的instanceof

  • go group并发执行

    go group并发执行

腾讯云代理商
海外云服务器