ロックは、パフォーマンスや精度の問題を引き起こす可能性があります。ロックを初めて使用する場合は、次の問題に注意してください。
デッドロックは、複数のスレッドが 1 つ以上のロックを取得しようとして、それぞれスレッドが異なるロックを保持しているときに発生します。デッドロックは次のような場合に発生します。
スレッドのサイクルがある場合。
各スレッドが少なくとも 1 つのロックを mutex 上で保持し、すでにロックを保持しているサイクルにある次の スレッドを mutex 上で待機している場合。
どのスレッドもロックを解放しない場合。
例えば、交差点での交通渋滞を考えてみてください。それぞれの車は道路の一部を "取得" していますが、車が前へ進むためには、別の車がいる前方の道路を "取得" する必要があります。デッドロックを回避するには、次の 3 つの一般的な方法があります。
同時に 2 つのロックを使用する状況を回避する。プログラムを小さなコードに分割して、1 つのロックを保持している間にそれぞれが処理を終了できるようにします。
常に同じ順序でロックを取得する。例えば、"外部コンテナー" mutex と "内部コンテナー" mutex があり、それぞれが 1 つのロックを必要とする場合は、常に "外側" が先にロックを取得するようにします。別の例は、ロックに名前があり、"アルファベット順にロックを取得" する場合です。ロックに名前がない場合は、mutex の数値アドレス順でロックを取得します。
ロックの代わりにアトミック操作を使用する。
もう 1 つのロックの問題はコンボイ です。コンボイは、ロックを保持しているスレッドがオペレーティング・システムにより中断されたときに発生します。その他のスレッドは、中断されたスレッドが再開し、ロックを解放するまで待機しなければなりません。フェアな mutex では、待機スレッドが中断された場合にその後続のすべてのスレッドが待機しなければならないため、状況を悪化させてしまいます。
コンボイを最小限に抑えるには、ロックをできるだけ短時間で解放します。また、ロックを取得する前にできるだけ事前に処理しておきます。
コンボイを回避するため、できる限りロックの代わりにアトミック操作を使用してください。