std::counting_semaphore, std::binary_semaphore
ヘッダ <semaphore> で定義 | ||
template<std::ptrdiff_t LeastMaxValue =/* implementation-defined */> class counting_semaphore; | (1) | (C++20以上) |
using binary_semaphore = std::counting_semaphore<1>; | (2) | (C++20以上) |
counting_semaphore
は共有リソースへのアクセスを制御できる軽量な同期プリミティブです。 std::mutex と異なり、 counting_semaphore
は同じリソースに対する複数の (少なくとも LeastMaxValue
個の) 並行アクセスを許可できます。 LeastMaxValue
が負の場合、プログラムは ill-formed です。binary_semaphore
は LeastMaxValue
が 1 の std::counting_semaphore のエイリアスです。 処理系は std::counting_semaphore のデフォルトの実装よりも効率良く binary_semaphore
を実装しても構いません。counting_semaphore
はコンストラクタによって初期化されるカウンタを内部に持ちます。 このカウンタは acquire() およびその関連メソッドの呼び出しによってデクリメントされ、 release() の呼び出しによってインクリメントされます。 カウンタがゼロのときは、 acquire() はカウンタがインクリメントされるまでブロックしますが、 try_acquire() はブロックしません。 try_acquire_for() および try_acquire_until() はカウンタがインクリメントされるかタイムアウトが満了するまでブロックします。
std::condition_variable の wait() と同様に、 counting_semaphore
の try_acquire() はスプリアスに失敗することがあります。
テンプレートクラス std::counting_semaphore
は DefaultConstructible でも CopyConstructible でも MoveConstructible でも CopyAssignable でも MoveAssignable でもありません。
目次 |
[編集]メンバ関数
counting_semaphore を構築します (パブリックメンバ関数) | |
counting_semaphore を破棄します (パブリックメンバ関数) | |
operator= [削除] | counting_semaphore は代入可能ではありません (パブリックメンバ関数) |
操作 | |
内部カウンタをインクリメントし、取得側スレッドのブロックを解除します (パブリックメンバ関数) | |
内部カウンタをデクリメントします。 できない場合はできるまでブロックします (パブリックメンバ関数) | |
ブロックせずに内部カウンタのデクリメントを試みます (パブリックメンバ関数) | |
内部カウンタのデクリメントを試みます。 指定した時間ブロックします (パブリックメンバ関数) | |
内部カウンタのデクリメントを試みます。 指定した時点までブロックします (パブリックメンバ関数) | |
定数 | |
[静的] | 内部カウンタの可能な最大値を返します (パブリック静的メンバ関数) |
[編集]ノート
その名前が示すように、 LeastMaxValue
は最小の最大値であり、実際の最大値ではありません。 そのため、 max() は LeastMaxValue
より大きな値を返すことがあります。
std::mutex と異なり、 counting_semaphore
はスレッドに紐付きません。 例えば、セマフォを取得するスレッドとセマフォを解放するスレッドが違っても構いません。 counting_semaphore
のすべての操作は並行的に行うことができ、特定のスレッドといかなる関係も持ちません。 ただし、デストラクタを並行的に実行することはできません (構築と異なるスレッドで実行することはできます)。
セマフォは相互排他だけでなく通知のためにもよく使用されます。 この場合、セマフォは 0 で初期化し、送信側が release(n) を呼んで通知するまで受信側が acquire() を試みてブロックします。 この点に関してセマフォは std::condition_variable の代替品と考えることができます (しばしば性能がより良いです)。
[編集]例
This section is incomplete Reason: no example |