Go言語

【Go言語】syncパッケージのOnceの使い方

Onceとは?

syncパッケージで定義されている。
Onceはアクションを1度のみ実行するオブジェクト。

OnceにはDoメソッドが定義されている。
Doメソッドは引数として渡された関数を、Onceのインスタンスで初めて呼び出される場合にのみ呼び出す。

  • Doメソッドを複数回実行しても、引数の関数を呼び出すのは初回のみ
  • 引数の関数が異なっていても、呼び出すのは初回のみ(同じOnceインスタンスであれば引数は関係ない)
  • 異なるゴルーチンで呼ばれたとしても、1度しか実行しない

Onceのサンプルコード

変数countを10個のゴルーチンからインクリメントしている。
ただし、インクリメントの関数はOnce.Doで呼び出しています。

package main

import (
    "fmt"
    "sync"
)

func main() {
    var count int
    increment := func() {
        count++
    }

    var once sync.Once
    var wg sync.WaitGroup
    wg.Add(10)
    for i := 0; i < 10; i++ {
        go func() {
            defer wg.Done()
            once.Do(increment)
        }()
    }

    wg.Wait()
    fmt.Printf("Count: %d\n", count)
}

Go Playground: https://play.golang.org/p/cJ8r_meJm9n

結果は、「Count: 1

異なるゴルーチン間でもOnce.Doに渡した関数が1度しか呼び出されていないのが確認できます。
 

参考図書

Tour of Goを終えた人にオススメです!!

イチオシ記事

1

自己紹介 フリーランスエンジニアをしているヨノと申します。 独学でプログラミングを学び、ソシャゲ・SaaS開発などを経て、2018年からフリーランスエンジニアとして活動しています。 主にバックエンド中 ...

2

はじめまして、フリーランスエンジニアのヨノと申します。 自己紹介 独学でプログラミングを学び、ソシャゲ・SaaS開発などを経て、2018年からフリーランスエンジニアとして活動しています。 主にバックエ ...

3

ネット上で色々言われているフリーランスエンジニア....。「本当はどうなの?」と思っている人は多いでしょう。 そこで本記事ではフリーランスエンジニア5年生の私が、ネット上の意見も引用しながら実態を解説 ...

-Go言語