3

静的フィールドではないダブルチェックロックを使用するのは正しいですか?

class Foo
{ 
   private SomeType member;
   private readonly object memeberSync = new object();
   public SomeType Memeber
   { 
      get
      {
         if(member == null)
         { 
            lock(memeberSync)
            {
               if(member == null)
               {
                  member = new SomeType();
               } 
            }
         }
         return object;
      }
   }
}
4

3 に答える 3

6

静的フィールドではないダブルチェックロックを使用するのは正しいですか?

はい、二重チェックを使用してスレッドセーフ遅延読み込みlockを取得するコードに問題はありません。.NET 4 から使用している場合は、Lazyクラスを使用することをお勧めします。このアプローチでは、スレッド セーフ遅延読み込みを使用しても同じ結果が得られますが、コードがよりシンプルになり、読みやすくなります。

class Foo
{
    private readonly Lazy<SomeType> _member = 
                                   new Lazy<SomeType>(() => new SomeType());

    public SomeType Member
    {
        get { return _member.Value; }
    }
}
于 2012-10-24T08:34:17.467 に答える
2

member外部チェックは、一度初期化されると、プロパティにアクセスするたびにロックを取得する必要がないという点で、パフォーマンスを向上させます。複数のスレッドからプロパティに頻繁にアクセスしている場合、ロックのパフォーマンス ヒットは非常に顕著になる可能性があります。

競合状態を防ぐには内部チェックが必要です。それがないと、2 つのスレッドが外部ifステートメントを処理し、両方が初期化される可能性がありますmember

厳密に言えば、outerif必要ありませんが、良い習慣と見なされており、(スレッドの多いアプリケーションでは) パフォーマンス上の利点が顕著になります。

于 2012-10-24T08:32:57.620 に答える
0

別のロックが解放されるまでロックが適用されない可能性があるため、これは推奨される方法です。

この場合、2 つのスレッドが同時に getter にアクセスし、最初のスレッドがロックを取得し、2 番目のスレッドが待機します。

最初のスレッドが完了すると、2 番目のスレッドがロックされます。

これが可能な場合は、現在のスレッドがロックを取得する前に、変数が別のスレッドによってすでに作成されているかどうかを確認する必要があります。

于 2012-10-24T08:30:31.450 に答える