日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程语言 > php >内容正文

php

php协程和goroutine,golang中四种方式实现子goroutine与主协程的同步

發布時間:2023/12/19 php 32 豆豆
生活随笔 收集整理的這篇文章主要介紹了 php协程和goroutine,golang中四种方式实现子goroutine与主协程的同步 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

如何實現子goroutine與主線程的同步

第一種方式:time.sleep(),這種方式很太死板,就不演示了。

第二種方式:使用channel機制,每個goroutine傳一個channel進去然后往里寫數據,在再主線程中讀取這些channel,直到全部讀到數據了子goroutine也就全部運行完了,那么主goroutine也就可以結束了。這種模式是子線程去通知主線程結束。

package main

import (

"fmt"

)

func main() {

var chanTest = make(chan int)

var chanMain = make(chan int)

go func() {

for i := 0; i < 20; i++ {

chanTest

fmt.Println("生產者寫入數據", i)

}

close(chanTest)

}()

go func() {

for v := range chanTest {

fmt.Println("\t消費者讀出數據", v)

}

chanMain

}()

go func() {

for v := range chanTest {

fmt.Println("\t\t消費者讀出數據", v)

}

chanMain

}()

}

第三種方式:使用context中cancel函數,這種模式是主線程去通知子線程結束。

package main

import (

"context"

"fmt"

"time"

)

func gen(ctx context.Context)

dst := make(chan int)

n := 1

go func() {

for {

select {

case

fmt.Println("i exited")

return // returning not to leak the goroutine

case dst

n++

}

}

}()

return dst

}

func test() {

ctx, cancel := context.WithCancel(context.Background())

defer cancel() // cancel when we are finished consuming integers

intChan := gen(ctx)

for n := range intChan {

fmt.Println(n)

if n == 5 {

break

}

}

}

func main() {

test()

time.Sleep(time.Hour)

}

第四種方式:sync.WaitGroup模式,Add方法設置等待子goroutine的數量,使用Done方法設置等待子goroutine的數量減1,當等待的數量等于0時,Wait函數返回。

//使用golang中sync.WaitGroup來實現協程同步

package main

import (

"fmt"

"net/http"

"io/ioutil"

"time"

"os"

"sync"

)

var waitGroup = new(sync.WaitGroup)

func download(i int ){

url := fmt.Sprintf("http://pic2016.ytqmx.com:82/2016/0919/41/%d.jpg", i)

fmt.Printf("開始下載:%s\n", url)

res,err := http.Get(url)

if err != nil || res.StatusCode != 200{

fmt.Printf("下載失敗:%s", res.Request.URL)

}

fmt.Printf("開始讀取文件內容,url=%s\n", url)

data ,err2 := ioutil.ReadAll(res.Body)

if err2 != nil {

fmt.Printf("讀取數據失敗")

}

ioutil.WriteFile(fmt.Sprintf("pic2016/1_%d.jpg", i), data, 0644)

//計數器-1

waitGroup.Done()

}

func main() {

//創建多個協程,同時下載多個圖片

os.MkdirAll("pic2016", 0666)

now := time.Now()

for i :=1; i<24; i++ {

//計數器+1

waitGroup.Add(1)

go download(i)

}

//等待所有協程操作完成

waitGroup.Wait()

fmt.Printf("下載總時間:%v\n", time.Now().Sub(now))

}

總結

以上是生活随笔為你收集整理的php协程和goroutine,golang中四种方式实现子goroutine与主协程的同步的全部內容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。