使用golang编写一个并发工作队列


Posted in Golang onMay 08, 2021

其实golang用一个函数可以构建一个并发队列,现在编写一个灵活可控的队列程序

先定义一个工作

type Worker struct {
    ID      int
    RepJobs chan int64
    SM      *SM
    quit    chan bool
}

包含了workid和执行任务的id,上面的SM只是任务具体内容,这个和具体业务相关,大家自己编写自己的SM业务逻辑

然后定义工作池

type workerPool struct {
    workerChan chan *Worker
    workerList []*Worker
}

这个里面定义了一个工作队列的切片,可以自定义工作队列的个数,甚至后期还可以添加work,还定义了一个队列类型的管道。

定义完成过后就可以初始化工作池了

func InitWorkerPool() error {
    n := 3
    WorkerPool = &workerPool{
        workerChan: make(chan *Worker, n),
        workerList: make([]*Worker, 0, n),
    }
    for i := 0; i < n; i++ {
        worker := NewWorker(i)
        WorkerPool.workerList = append(WorkerPool.workerList, worker)
        worker.Start()
        log.Debugf("worker %d started", worker.ID)
    }
    return nil
}

这个里面我写死了worker的个数是3,当然这个可以通过读取配置文件或者参数传递的方式;这个里面逐一启动work

worker.Start(),这个是关键

func (w *Worker) Start() {
    go func() {
        for {
            WorkerPool.workerChan <- w
            select {
            case jobID := <-w.RepJobs:
                log.Debugf("worker: %d, will handle job: %d", w.ID, jobID)
                w.handleRepJob(jobID)
            case q := <-w.quit:
                if q {
                    log.Debugf("worker: %d, will stop.", w.ID)
                    return
                }
            }
        }
    }()
}

这个就是go 启动一个协程,先把自己放到workerChan中,然后不断从w.RepJobs管道中获取任务并执行,如果执行完成后又把自己放回到队列中。

所以如果你要有任务需要执行,放到这个管道中即可

func Dispatch() {
    for {
        select {
        case job := <-jobQueue:
            go func(jobID int64) {
                println("Trying to dispatch job: %d", jobID)
                worker := <-WorkerPool.workerChan
                worker.RepJobs <- jobID
            }(job)
        }
    }
}

从管道中拿出一个worker并把任务id放到worker中去执行。

当然你可以停止worker,甚至可以停止job

func (w *Worker) Stop() {
    go func() {
        w.quit <- true
    }()
}
func (wp *workerPool) StopJobs(jobs []int64) {
    log.Debugf("Works working on jobs: %v will be stopped", jobs)
    for _, id := range jobs {
        for _, w := range wp.workerList {
            if w.SM.JobID == id {
                log.Debugf("found a worker whose job ID is %d, will try to stop it", id)
                w.SM.Stop(id)
            }
        }
    }
}

补充一下,int64和字符串转换。

string到int

int,err:=strconv.Atoi(string)

string到int64

int64, err := strconv.ParseInt(string, 10, 64)

int到string

string:=strconv.Itoa(int)

int64到string

string:=strconv.FormatInt(int64,10)

以上为个人经验,希望能给大家一个参考,也希望大家多多支持三水点靠木。如有错误或未考虑完全的地方,望不吝赐教。

Golang 相关文章推荐
golang中实现给gif、png、jpeg图片添加文字水印
Apr 26 Golang
golang json数组拼接的实例
Apr 28 Golang
Go语言中break label与goto label的区别
Apr 28 Golang
go语言中GOPATH GOROOT的作用和设置方式
May 05 Golang
Golang中channel的原理解读(推荐)
Oct 16 Golang
Go语言实现一个简单的并发聊天室的项目实战
Mar 18 Golang
Go语言特点及基本数据类型使用详解
Mar 21 Golang
golang实现浏览器导出excel文件功能
Mar 25 Golang
Golang 1.18 多模块Multi-Module工作区模式的新特性
Apr 11 Golang
Go web入门Go pongo2模板引擎
May 20 Golang
GoFrame gredis缓存DoVar Conn连接对象 自动序列化GoFrame gredisDo/DoVar方法Conn连接对象自动序列化/反序列化总结
Jun 14 Golang
Go 内联优化让程序员爱不释手
Jun 21 Golang
Go 在 MongoDB 中常用查询与修改的操作
May 07 #Golang
golang 实现时间戳和时间的转化
May 07 #Golang
Golang Gob编码(gob包的使用详解)
May 07 #Golang
go mod 安装依赖 unkown revision问题的解决方案
解决golang 关于全局变量的坑
May 06 #Golang
Goland使用Go Modules创建/管理项目的操作
解决goland 导入项目后import里的包报红问题
You might like
Js+Dhtml:WEB程序员简易开发工具包(预先体验版)
2006/11/07 Javascript
JQUERY复选框CHECKBOX全选,取消全选
2008/08/30 Javascript
ExtJs3.0中Store添加 baseParams 的Bug
2010/03/10 Javascript
利用google提供的API(JavaScript接口)获取网站访问者IP地理位置的代码详解
2010/07/24 Javascript
关于JQuery($.load)事件的用法和分析
2013/04/09 Javascript
JSF中confirm弹出框的用法示例介绍
2014/01/07 Javascript
纯js实现div内图片自适应大小(已测试,兼容火狐)
2014/06/16 Javascript
js读写json文件实例代码
2014/10/21 Javascript
javascript常用代码段搜集
2014/12/04 Javascript
JQuery自动触发事件的方法
2015/06/13 Javascript
JS中使用DOM来控制HTML元素
2016/07/31 Javascript
JS获取和修改元素样式的实例代码
2016/08/06 Javascript
jQuery实现的右下角广告窗体跟随效果示例
2016/09/16 Javascript
JS 动态判断PC和手机浏览器实现代码
2016/09/21 Javascript
基于webpack 实用配置方法总结
2017/09/28 Javascript
es6数值的扩展方法
2019/03/11 Javascript
Vue编写可显示周和月模式的日历 Vue自定义日历内容的显示
2019/06/26 Javascript
Python中的列表知识点汇总
2015/04/14 Python
Python连接DB2数据库
2016/08/27 Python
python实现决策树C4.5算法详解(在ID3基础上改进)
2017/05/31 Python
python使用正则表达式的search()函数实现指定位置搜索功能
2017/11/10 Python
代码分析Python地图坐标转换
2018/02/08 Python
为什么入门大数据选择Python而不是Java?
2018/03/07 Python
Python的条件表达式和lambda表达式实例
2019/01/31 Python
用python打印菱形的实操方法和代码
2019/06/25 Python
django中使用POST方法获取POST数据
2019/08/20 Python
python计算n的阶乘的方法代码
2019/10/25 Python
opencv3/python 鼠标响应操作详解
2019/12/11 Python
python如何通过twisted搭建socket服务
2020/02/03 Python
解决keras GAN训练是loss不发生变化,accuracy一直为0.5的问题
2020/07/02 Python
canvas绘制太极图的实现示例
2020/04/29 HTML / CSS
集体备课反思
2014/02/12 职场文书
《石榴》教学反思
2014/03/02 职场文书
2015年度环卫处工作总结
2015/07/24 职场文书
2016年校园植树节广播稿
2015/12/17 职场文书
2016大学优秀学生干部事迹材料
2016/03/01 职场文书