欧美bbbwbbbw肥妇,免费乱码人妻系列日韩,一级黄片

GoLang中的sync包Once使用執(zhí)行示例

 更新時間:2023年03月06日 10:43:57   作者:水淹萌龍  
這篇文章主要介紹了GoLang中的sync包Once使用執(zhí)行示例,沒有學(xué)習(xí)Once前,大家可能想到 聲明一個標(biāo)識,表示是否初始化過,然后初始化這個標(biāo)識加鎖,更新這個標(biāo)識,Once包主要用于在并發(fā)執(zhí)行代碼的時候,某部分代碼只會被執(zhí)行一次

背景

在系統(tǒng)初始化的時候,某些代碼只想被執(zhí)行一次,這時應(yīng)該怎么做呢,沒有學(xué)習(xí) Once 前,大家可能想到 聲明一個標(biāo)識,表示是否初始化過,然后初始化這個標(biāo)識加鎖,更新這個標(biāo)識。

但是學(xué)會了 One 的使用可以更加簡單的解決這個問題

One簡介

Once 包主要用于在并發(fā)執(zhí)行代碼的時候,某部分代碼只會被執(zhí)行 一次。

Once 的使用也非常簡單,Once 只有一個 Do 方法,接收一個無參數(shù)無返回值的函數(shù)類型的參數(shù) f,不管調(diào)用多少次 Do 方法,參數(shù) f 只在第一次調(diào)用 Do 方法時執(zhí)行。

示例

我們有一個Msg 參數(shù),多個協(xié)程都會用到他,但是這個參數(shù)只用初始化一次就可以。

package main
import (
	"fmt"
	"sync"
	"time"
)
var msg string
func main() {
	var one sync.Once
	for i := 0; i < 5; i++ {
		go func(i int) {
			one.Do(func() { 
				fmt.Printf("%d 執(zhí)行初始化!\n", i)
				msg = "Your Need Data"
			})
			fmt.Println(msg)
		}(i)
	}
	time.Sleep(3* time.Second)
}

執(zhí)行結(jié)果如下:

可以看到初始化的代碼只被4號線程執(zhí)行了一次, 其他協(xié)程都是直接讀的初始化的數(shù)據(jù),并沒有執(zhí)行初始化的函數(shù)。

注意

不要在 Do() 方法的參數(shù)方法中再次調(diào)用Do() 方法,因?yàn)閳?zhí)行這個Do() 方法的參數(shù)方法的時候,One 會持有一個鎖,如果再參數(shù)方法中再次調(diào)用Do() 方法,就會等待這個鎖釋放, 導(dǎo)致參數(shù)方法無法執(zhí)行完畢,然后外層的Do 方法就一直無法釋放鎖,最后就成了死鎖。

錯誤示例:

package main
import (
	"fmt"
	"sync"
)
var msg string
var one sync.Once
func main() {
	one.Do(fun1)
}
func fun1(){
	fmt.Println("我是 fun1")
	one.Do(fun2)
}
func fun2(){
	fmt.Println("我是 fun2")
}

執(zhí)行結(jié)果:

可以知道再 fun1() 中使用 Do() 方法調(diào)用 fun2 的時候形成了死鎖, 因?yàn)樵?fun1() 執(zhí)行過程中已將持有了該鎖,需要 fun1() 執(zhí)行完畢才會釋放,然后因?yàn)槭褂?Do() 方法執(zhí)行 fun2() 也會請求這個鎖, 會一直等待,導(dǎo)致 fun1() 不可能執(zhí)行完, 也不可能釋放鎖。成了死鎖。

源碼解讀

查看源碼

func (o *Once) Do(f func()) {
	if atomic.LoadUint32(&o.done) == 0 {
		// Outlined slow-path to allow inlining of the fast-path.
		o.doSlow(f)
	}
}
func (o *Once) doSlow(f func()) {
	o.m.Lock()
	defer o.m.Unlock()
	if o.done == 0 {
		defer atomic.StoreUint32(&o.done, 1)
		f()
	}
}

使用一個原子類作為標(biāo)識,加鎖校驗(yàn)和操作原子類,保證只會被一個協(xié)程執(zhí)行。

Do 調(diào)用了 doSlow , 在 doSlow 中有defer 關(guān)鍵字,表示執(zhí)行函數(shù)和釋放鎖是倒序執(zhí)行,必須先執(zhí)行完畢 if 判斷和里面的 f() 才能釋放鎖。

到此這篇關(guān)于GoLang中的sync包Once使用執(zhí)行示例的文章就介紹到這了,更多相關(guān)Go sync Once內(nèi)容請搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!

相關(guān)文章

  • Go框架三件套Gorm?Kitex?Hertz基本用法與常見API講解

    Go框架三件套Gorm?Kitex?Hertz基本用法與常見API講解

    這篇文章主要為大家介紹了Go框架三件套Gorm?Kitex?Hertz的基本用法與常見API講解,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進(jìn)步,早日升職加薪<BR>
    2023-02-02
  • Golang算法問題之?dāng)?shù)組按指定規(guī)則排序的方法分析

    Golang算法問題之?dāng)?shù)組按指定規(guī)則排序的方法分析

    這篇文章主要介紹了Golang算法問題之?dāng)?shù)組按指定規(guī)則排序的方法,結(jié)合實(shí)例形式分析了Go語言數(shù)組排序相關(guān)算法原理與操作技巧,需要的朋友可以參考下
    2017-02-02
  • go gin+token(JWT)驗(yàn)證實(shí)現(xiàn)登陸驗(yàn)證

    go gin+token(JWT)驗(yàn)證實(shí)現(xiàn)登陸驗(yàn)證

    本文主要介紹了go gin+token(JWT)驗(yàn)證實(shí)現(xiàn)登陸驗(yàn)證,文中通過示例代碼介紹的非常詳細(xì),具有一定的參考價值,感興趣的小伙伴們可以參考一下
    2021-12-12
  • golang時間字符串和時間戳轉(zhuǎn)換的案例

    golang時間字符串和時間戳轉(zhuǎn)換的案例

    這篇文章主要介紹了golang時間字符串和時間戳轉(zhuǎn)換的案例,具有很好的參考價值,希望對大家有所幫助。一起跟隨小編過來看看吧
    2020-12-12
  • win10下go mod配置方式

    win10下go mod配置方式

    這篇文章主要介紹了win10下go mod配置方式,具有很好的參考價值,希望對大家有所幫助。一起跟隨小編過來看看吧
    2021-04-04
  • 如何使用工具自動監(jiān)測SSL證書有效期并發(fā)送提醒郵件

    如何使用工具自動監(jiān)測SSL證書有效期并發(fā)送提醒郵件

    本文介紹了如何開發(fā)一個工具,用于每日檢測SSL證書剩余有效天數(shù)并通過郵件發(fā)送提醒,工具基于命令行,通過SMTP協(xié)議發(fā)送郵件,需配置SMTP連接信息,本文還提供了配置文件樣例及代碼實(shí)現(xiàn),幫助用戶輕松部署和使用該工具
    2024-10-10
  • 一文秒懂Go 編寫命令行工具的代碼

    一文秒懂Go 編寫命令行工具的代碼

    這篇文章主要介紹了一文秒懂Go 編寫命令行工具的代碼,本文給大家介紹的非常詳細(xì),對大家的學(xué)習(xí)或工作具有一定的參考借鑒價值,需要的朋友可以參考下
    2021-01-01
  • 使用Go實(shí)現(xiàn)郵箱驗(yàn)證碼API功能

    使用Go實(shí)現(xiàn)郵箱驗(yàn)證碼API功能

    本文將帶你了解一個項(xiàng)目如何實(shí)現(xiàn)一個郵箱驗(yàn)證接口,即一個可用的發(fā)送郵箱驗(yàn)證碼API和驗(yàn)證驗(yàn)證碼是否正確功能,對Go實(shí)現(xiàn)郵箱驗(yàn)證碼API詳細(xì)過程感興趣的朋友一起看看吧
    2024-06-06
  • 如何使用Golang創(chuàng)建與讀取Excel文件

    如何使用Golang創(chuàng)建與讀取Excel文件

    我最近工作忙于作圖,圖表,需要自己準(zhǔn)備數(shù)據(jù)源,所以經(jīng)常和Excel打交道,下面這篇文章主要給大家介紹了關(guān)于如何使用Golang創(chuàng)建與讀取Excel文件的相關(guān)資料,需要的朋友可以參考下
    2022-07-07
  • Go語言學(xué)習(xí)之context包的用法詳解

    Go語言學(xué)習(xí)之context包的用法詳解

    日常Go開發(fā)中,Context包是用的最多的一個了,幾乎所有函數(shù)的第一個參數(shù)都是ctx,那么我們?yōu)槭裁匆獋鬟fContext呢,Context又有哪些用法,底層實(shí)現(xiàn)是如何呢?相信你也一定會有探索的欲望,那么就跟著本篇文章,一起來學(xué)習(xí)吧
    2022-10-10

最新評論