亚洲乱码中文字幕综合,中国熟女仑乱hd,亚洲精品乱拍国产一区二区三区,一本大道卡一卡二卡三乱码全集资源,又粗又黄又硬又爽的免费视频

4個場景教會你Go中Goroutine和通道是怎么用的

 更新時間:2023年05月26日 10:28:19   作者:不背鍋運維  
本篇給出了4個在運維開發(fā)工作中較為常見的且也是比較典型的場景,通過這些場景來帶大家掌握Go中Goroutine和通道是怎么使用的,需要的可以學習一下

開篇

這段時間把主要精力都放在了K8S上,差點把Golang給忘了。那本篇就分享一下并發(fā)相關的內容(Goroutine和通道)。 本篇給出4個場景,這4個場景是在運維開發(fā)工作中較為常見的且也是比較典型的場景。通過這些代碼示例,讓你知道Goroutine和通道在運維開發(fā)中是怎么應用的??偠灾?,言而總之,當涉及到處理并發(fā)和并行任務時,Goroutine和通道是非常強悍的,可以讓我們開發(fā)出高效的、牛逼的并發(fā)程序。

實戰(zhàn)場景

1.并發(fā)執(zhí)行任務的場景

場景:假設需要編寫一個程序,用于批量執(zhí)行某個操作(例如部署應用程序、更新配置等)到多臺服務器上。

供參考的代碼示例:

package?main

import?(
?"fmt"
?"sync"
)

//?服務器結構體
type?Server?struct?{
?Name?string
?//?其他服務器相關的字段
}

//?執(zhí)行任務的函數
func?executeTask(server?Server,?task?string)?{
?//?連接服務器并執(zhí)行任務的邏輯
?fmt.Printf("執(zhí)行任務?[%s]?到服務器?[%s]\n",?task,?server.Name)
?//?執(zhí)行操作的代碼
}

func?main()?{
?//?服務器列表
?servers?:=?[]Server{
??{Name:?"Server1"},
??{Name:?"Server2"},
??{Name:?"Server3"},
??//?添加更多的服務器
?}

?//?任務列表
?tasks?:=?[]string{"部署應用程序",?"更新配置",?"執(zhí)行命令",?"其他任務"}

?//?創(chuàng)建一個任務通道,用于發(fā)送任務到Goroutine池
?taskChannel?:=?make(chan?string)

?//?創(chuàng)建一個等待組,用于等待所有Goroutine執(zhí)行完畢
?var?wg?sync.WaitGroup
?wg.Add(len(servers))

?//?啟動Goroutine池
?for?_,?server?:=?range?servers?{
??go?func(server?Server)?{
???//?標記任務完成時,通知等待組減少一個計數
???defer?wg.Done()

???//?從任務通道中接收任務,并執(zhí)行
???for?task?:=?range?taskChannel?{
????executeTask(server,?task)
???}
??}(server)
?}

?//?將任務發(fā)送到任務通道
?for?_,?task?:=?range?tasks?{
??taskChannel?<-?task
?}

?//?關閉任務通道,表示所有任務都已發(fā)送
?close(taskChannel)

?//?等待所有Goroutine執(zhí)行完畢
?wg.Wait()
}

上面的代碼,創(chuàng)建了一個Goroutine池,每個Goroutine代表一臺服務器,通過通道將任務分發(fā)給Goroutine進行并發(fā)執(zhí)行。每個Goroutine負責連接到服務器,并執(zhí)行相應的操作。這樣可以加速任務的執(zhí)行,同時提高資源利用率。

2.并發(fā)日志處理的場景

場景:假設需要將大量的日志數據并發(fā)地寫入到不同的目標中(例如文件、數據庫、消息隊列等)。

供參考的代碼示例:

package?main

import?(
?"fmt"
?"log"
?"os"
?"sync"
)

//?日志結構體
type?Log?struct?{
?Message?string
?//?其他日志相關的字段
}

func?main()?{
?//?創(chuàng)建一個日志通道,用于發(fā)送日志數據
?logChannel?:=?make(chan?Log)

?//?創(chuàng)建一個等待組,用于等待所有Goroutine執(zhí)行完畢
?var?wg?sync.WaitGroup

?//?啟動一個Goroutine處理日志寫入操作
?wg.Add(1)
?go?func()?{
??//?標記日志寫入完畢時,通知等待組減少一個計數
??defer?wg.Done()

??//?打開文件進行日志寫入
??file,?err?:=?os.OpenFile("log.txt",?os.O_APPEND|os.O_CREATE|os.O_WRONLY,?0644)
??if?err?!=?nil?{
???log.Fatal(err)
??}
??defer?file.Close()

??//?創(chuàng)建一個日志寫入器
??logger?:=?log.New(file,?"",?log.LstdFlags)

??//?從日志通道中接收日志數據,并寫入到目標中
??for?log?:=?range?logChannel?{
???logger.Println(log.Message)
??}
?}()

?//?并發(fā)地向日志通道發(fā)送日志數據
?for?i?:=?0;?i?<?10;?i++?{
??wg.Add(1)
??go?func(index?int)?{
???//?標記發(fā)送完日志數據時,通知等待組減少一個計數
???defer?wg.Done()

???//?構造日志數據
???log?:=?Log{
????Message:?fmt.Sprintf("日志消息?%d",?index),
????//?設置其他日志字段
???}

???//?發(fā)送日志數據到日志通道
???logChannel?<-?log
??}(i)
?}

?//?關閉日志通道,表示所有日志數據都已發(fā)送
?close(logChannel)

?//?等待日志寫入操作的Goroutine執(zhí)行完畢
?wg.Wait()
}

在上面的代碼中,使用了一個專門的Goroutine來處理日志寫入操作,該Goroutine從一個日志通道中讀取日志數據,并將其寫入到目標中。其他的Goroutine可以并發(fā)地向該通道發(fā)送日志數據,而不會因為寫入操作而阻塞。

3.異步任務調度的場景

在實際的運維工作中,有種場景是需要按照一定的調度策略異步執(zhí)行一些任務。比如這樣的場景:定期備份數據庫、定時清理無效數據等。

供參考的代碼示例:

package?main

import?(
?"fmt"
?"time"
)

//?執(zhí)行任務的函數
func?executeTask(task?string)?{
?//?執(zhí)行任務的邏輯
?fmt.Println("執(zhí)行任務:",?task)
?//?具體的任務操作代碼
}

func?main()?{
?//?創(chuàng)建一個定時器,每隔一段時間觸發(fā)一次
?timer?:=?time.NewTimer(5?*?time.Second)

?//?啟動一個Goroutine等待定時器的觸發(fā)事件
?go?func()?{
??//?等待定時器的觸發(fā)事件
??<-timer.C
??//?定時器觸發(fā)后執(zhí)行任務
??executeTask("定時任務1")
??//?重新設置定時器,以實現(xiàn)循環(huán)調度
??timer.Reset(10?*?time.Second)
?}()

?//?主線程繼續(xù)執(zhí)行其他任務
?//?...

?//?阻塞主線程,保持程序運行
?select?{}
}

4.并發(fā)任務協(xié)作的場景

在某些情況下,你可能需要多個Goroutine之間進行協(xié)作和同步。例如,一個Goroutine負責生產任務,而另一個Goroutine負責消費任務并進行處理。你可以使用通道來實現(xiàn)生產者-消費者模型。生產者將任務發(fā)送到通道中,而消費者從通道中接收任務并進行處理。通過這種方式,可以實現(xiàn)任務的有效分配和協(xié)同處理。

package?main

import?(
?"fmt"
?"time"
)

//?任務結構體
type?Task?struct?{
?ID???int
?Data?string
?//?其他任務相關的字段
}

//?生產者,負責生產任務并發(fā)送到通道
func?producer(ch?chan<-?Task)?{
?for?i?:=?1;?i?<=?10;?i++?{
??task?:=?Task{
???ID:???i,
???Data:?fmt.Sprintf("任務?%d",?i),
???//?設置其他任務字段
??}
??ch?<-?task
??fmt.Println("生產任務:",?task.Data)
??time.Sleep(500?*?time.Millisecond)?//?模擬生產任務的耗時
?}
?close(ch)?//?關閉通道,表示所有任務都已生產完畢
}

//?消費者,負責從通道接收任務并進行處理
func?consumer(ch?<-chan?Task)?{
?for?task?:=?range?ch?{
??fmt.Println("消費任務:",?task.Data)
??//?執(zhí)行任務的處理邏輯
??time.Sleep(1?*?time.Second)?//?模擬處理任務的耗時
?}
}

func?main()?{
?//?創(chuàng)建一個任務通道,用于生產者和消費者之間的通信
?taskChannel?:=?make(chan?Task)

?//?啟動生產者Goroutine
?go?producer(taskChannel)

?//?啟動多個消費者Goroutine
?for?i?:=?1;?i?<=?3;?i++?{
??go?consumer(taskChannel)
?}

?//?阻塞主線程,保持程序運行
?select?{}
}

在上面的代碼種,使用了定時器(time.Timer)結合Goroutine來實現(xiàn)異步任務調度。通過啟動一個Goroutine來等待定時器的觸發(fā)事件,并執(zhí)行相應的任務。這樣可以在后臺自動執(zhí)行任務,而不需要阻塞主線程。

到此這篇關于4個場景教會你Go中Goroutine和通道是怎么用的的文章就介紹到這了,更多相關Go Goroutine通道內容請搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關文章希望大家以后多多支持腳本之家!

相關文章

  • 如何在Go中使用切片容量和長度

    如何在Go中使用切片容量和長度

    這篇文章主要介紹了如何在Go中使用切片容量和長度,文中通過示例代碼介紹的非常詳細,對大家的學習或者工作具有一定的參考學習價值,需要的朋友們下面隨著小編來一起學習學習吧
    2019-11-11
  • golang實現(xiàn)java uuid的序列化方法

    golang實現(xiàn)java uuid的序列化方法

    這篇文章主要介紹了golang實現(xiàn)java uuid的序列化方法,文中通過示例代碼介紹的非常詳細,對大家的學習或者工作具有一定的參考學習價值,需要的朋友們下面隨著小編來一起學習學習吧
    2020-09-09
  • CSP communicating sequential processes并發(fā)模型

    CSP communicating sequential processes并發(fā)模型

    這篇文章主要為大家介紹了CSP communicating sequential processes并發(fā)模型,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進步,早日升職加薪
    2022-05-05
  • Go語言異常處理error、panic、recover的使用

    Go語言異常處理error、panic、recover的使用

    GO語言中引入的異常的處理方式為error、panic、recover ,本文主要介紹了Go語言異常處理error、panic、recover的使用,感興趣的可以了解一下
    2024-08-08
  • Go?container包的介紹

    Go?container包的介紹

    這篇文章主要介紹了Go?container包,go語言container包中有List和Element容器ist和Element都是結構體類型。結構體類型有一個特點,那就是它們的零值都會是擁有其特定結構,但沒有任何定制化內容的值,相當于一個空殼,下面一起進文章來了解具體內容吧
    2021-12-12
  • go語言實現(xiàn)銀行卡號Luhn校驗

    go語言實現(xiàn)銀行卡號Luhn校驗

    這篇文章主要為大家介紹了go語言Luhn校驗測試銀行卡號碼的示例詳解,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進步,早日升職加薪
    2022-05-05
  • Go 語言中關于接口的三個

    Go 語言中關于接口的三個

    這篇文章主要介紹了Go 語言中關于接口的三個"潛規(guī)則",本文通過實例代碼相結合給大家介紹的非常詳細,對大家的學習或工作具有一定的參考借鑒價值,需要的朋友可以參考下
    2020-06-06
  • Go Asynq異步任務處理的實現(xiàn)

    Go Asynq異步任務處理的實現(xiàn)

    Asynq是一個新興的異步任務處理解決方案,它提供了輕量級的、易于使用的API,本文主要介紹了Go Asynq異步任務處理的實現(xiàn),具有一定的參考價值,感興趣的可以了解一下
    2023-06-06
  • go?singleflight緩存雪崩源碼分析與應用

    go?singleflight緩存雪崩源碼分析與應用

    這篇文章主要為大家介紹了go?singleflight緩存雪崩源碼分析與應用示例詳解,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進步,早日升職加薪
    2023-09-09
  • Golang語言如何高效拼接字符串詳解

    Golang語言如何高效拼接字符串詳解

    最近在做性能優(yōu)化,有個函數里面的耗時特別長,看里面的操作大多是一些字符串拼接的操作,而字符串拼接在 golang 里面其實有很多種實現(xiàn),下面這篇文章主要給大家介紹了關于Golang語言如何高效拼接字符串的相關資料,需要的朋友可以參考下
    2021-11-11

最新評論