zl程序教程

您现在的位置是:首页 >  Java

当前栏目

Golang高并发:生产者消费者模型

2023-02-26 10:20:49 时间

Golang高并发:生产者消费者模型

我们本篇博文主要通过几个例子来介绍生产者消费者模型。

案例1

下面看看第一个例子中的生产者协程。

(福利推荐:阿里云、腾讯云、华为云服务器最新限时优惠活动,云服务器1核2G仅88元/年、2核4G仅698元/3年,点击这里立即抢购>>>

//生产者协程     go func() {         for  {             product := strconv.Itoa(time.Now().Nanosecond())             chanShop <- "商品" + product             fmt.Println("生产了商品",product)              time.Sleep(1000 * time.Millisecond)         }     }()

生产者协程就是源源不断的生产,将时间转化为字符串,然后源源不断的产生产品字符串。此处用到了strconv.Itoa(),是将整型转换为字符串类型。time.Now()是当前的时间,而使用Nanosecond()是将其转换为纳秒。然后将得到的产品序列号字符串放入视频管道,然后输出生产了什么产品,然后睡一秒,然后接着生产。

至于消费者协程,我相信你已经猜到了是什么了,我们也来看一看吧。

//消费者协程     go func() {         for{             product := <-chanShop             fmt.Println("消费了产品",product)                          time.Sleep(time.Second)         }     }() 

每次从商品管道取一个产品,然后输出消费了什么产品,然后睡一秒,然后继续消费。

再来看看这个案例的主协程

//主协程     for  {         time.Sleep(time.Second)     }

运行结果是

消费了产品 商品607861100 生产了商品 607861100 生产了商品 607929500 消费了产品 商品607929500 生产了商品 608013000 消费了产品 商品608013000 生产了商品 608018400 消费了产品 商品608018400

没错,源源不断的生产消费、生产消费。

案例2

我们再来看看第二个案例,这个案例,我们引入了”物流“的概念。

先上主函数给各位读者老爷看看吧:

func main() {     chanStorage := make(chan string ,100)     chanShop := make(chan string, 100)      go producer(chanStorage)     go logistics(chanStorage,chanShop)     go consumer(chanShop)     for  {         time.Sleep(time.Second)     } }

主要是建立商店和物流两条管道,然后建立生产者、消费者、物流三条协程,然后主协程一直不go die

然后先来看看生产者协程

func producer(chanStorage chan string)  {     for i:=0;i<10;i++{         product := strconv.Itoa(time.Now().Nanosecond())         chanStorage <- "产品"+product         fmt.Println("生产了产品",product)         time.Sleep(time.Second)     }     close(chanStorage) }

和第一个案例一样,不过我们只生产10个产品放入仓库,然后关闭了仓库。

然后看看物流协程是干了些什么:

func logistics(chanStroge,chanShop chan string)  {     for p:= range chanStroge{         fmt.Println("物流完成转运",p)         chanShop <- p     }     fmt.Println("商品转运完毕!") }

源源不断扫描仓库,拿出商品然后将商品转运到商店。当生产者关闭仓库后,物流也停止转运了。

消费者不断在消费,然后看看消费者:

func consumer(chanShop chan string)  {     for{         product := <-chanShop         fmt.Println("消费了产品",product)     } }

等来一件商品,就卖出去。

然后看看运行结果

生产了产品 605763200物流完成转运 产品605763200消费了产品 产品605763200生产了产品 605826700物流完成转运 产品605826700消费了产品 产品605826700生产了产品 619889800物流完成转运 产品619889800消费了产品 产品619889800生产了产品 619906200物流完成转运 产品619906200消费了产品 产品619906200生产了产品 627948700物流完成转运 产品627948700消费了产品 产品627948700

我们可以看到,生产、转运、消费几乎是同时的。

因为我们当物流公司停止运物资时,商店也要关门,所以在物流协程内加入:

    close(chanShop)    fmt.Println("商品转运完毕!商店已关张!")

然后继续把消费者的for循环替换成

for product := range chanShop{        //product := <-chanShop        fmt.Println("消费了产品",product)        fmt.Println()    }    fmt.Println("消费全部完毕!")

就能够只读取管道里面的商品。

Golang高并发:生产者消费者模型


本站部分内容转载自网络,版权属于原作者所有,如有异议请联系QQ153890879修改或删除,谢谢!
转载请注明原文链接:Golang高并发:生产者消费者模型

你还在原价购买阿里云、腾讯云、华为云、天翼云产品?那就亏大啦!现在申请成为四大品牌云厂商VIP用户,可以3折优惠价购买云服务器等云产品,并且可享四大云服务商产品终身VIP优惠价,还等什么?赶紧点击下面对应链接免费申请VIP客户吧:

1、点击这里立即申请成为腾讯云VIP客户

2、点击这里立即注册成为天翼云VIP客户

3、点击这里立即申请成为华为云VIP客户

4、点击这里立享阿里云产品终身VIP优惠价

喜欢 (0)
[[email protected]]
分享 (0)