4
using System;

public sealed class Singleton
{
   private static volatile Singleton instance;
   private static object syncRoot = new Object();

   private Singleton() {}

   public static Singleton Instance
   {
      get 
      {
         if (instance == null) 
         {
            lock (syncRoot) 
            {
               if (instance == null) 
                  instance = new Singleton();
            }
         }

         return instance;
      }
   }
}

なぜダブルチェックなのかわかりません!このダブルチェックはスレッドの同時実行性の問題を解決するためのものだと読みましたが...

  1. ロックはそれを解決します-それで、なぜ最初に'if'をする必要があるのですか?

  2. このシングルトンに最初の'がない場合'それでもスレッドセーフになります-そうですか?

  3. 最初の'if'がfalseの場合、thread1は'instance'オブジェクトを初期化します=>今、'instance'はnullではなく、thread1はまだロックブロックにあります=== >>今、thread2は最初の'をチェックしますif'and will get false =>したがって、彼は' lock'に到達せず、すぐにインスタンスを返し、thread2は'インスタンス'のプロパティを変更できます=>したがって、thread1&&thread2は同じ'インスタンスで'動作しています' 'object =>なので、スレッドセーフはどこにありますか...またはここで欠落しているものです。

4

4 に答える 4

6

1.ロックはそれを解決します-それで、なぜ最初に'if'をする必要があるのですか?

したがって、シングルトンの新しいインスタンスを作成する必要がない限り、スレッドをロックすることはありません。
lock非常にコストのかかる操作なので、追加のチェックを行う価値があります。

2.このシングルトンに最初の'がない場合'それでもスレッドセーフになります-そうですか?

はい、しかしかなり遅いです。

3.Thread1 && thread2は、同じ「インスタンス」オブジェクトで「動作中」です=>したがって、スレッドセーフはどこにありますか

これがシングルトンの要点であり、すべてのスレッドに対して1つのインスタンスのみです。それはスレッドセーフなことです...

于 2012-05-10T23:41:32.367 に答える
2

lockThreadAが;の直前に中断された場合を想定しています。ThreadBはシングルトンの作成を正常に完了し、ThreadAが再開すると、ロックが解除されるとシングルトンの再作成を試みます。

于 2012-05-10T23:42:46.697 に答える
0

ifは、シングルトンがすでにインスタンス化されているかどうかをチェックし、インスタンス化されていない場合は、新しいインスタンスを作成します。そしてロックはスレッドセーフを保証します。

呼び出しごとに新しいインスタンスが作成される場合はありません(シングルトンのアイデアではありません)。ロックがないと、2つのスレッドが同時にインスタンスを作成できるため、2つのインスタンスが存在する可能性があります。

シングルスレッドのみを使用している場合は、ロックをワイプできます。それ以外の場合(mtで)それを使用することを強くお勧めします。

于 2012-05-10T23:42:25.580 に答える
0

これは、なぜそれが推奨されるのか(そしてなぜそれが最新の最適化コンパイラで常に機能するとは限らないのか)に関するメリーランド大学からの良い論文です。時間があればこれは良い読み物です。

http://www.cs.umd.edu/~pugh/java/memoryModel/DoubleCheckedLocking.html

于 2012-05-10T23:45:37.647 に答える