競態條件和死鎖。
如果兩個或多個線程訪問相同的對象,或者訪問不同步的共享狀態 ,就會出現競態條件;
為了避免出現該問題,可以鎖定共享的對象。但是過多的鎖定也會有麻煩,那就是死鎖;
當至少有兩個線程被掛起,等待對方解除鎖定。由於兩個線程都在等待對方,就出現了死鎖,線程將無限等下去;
要避免同步問題,最好不要在線程之間共享數據。當然,這並不總是可行的。如果需要共享數據,就必須使用同步技術;
確保一次只有一個線程訪問和改變共享狀態。注意,同步問題與競態條件和死鎖有關。如果不注意這些問題,就很難在應用程序中找到問題的原因,因為線程問題是不定期發生的。
------
多線程同時訪問一個實例對象時, 可以給進程加一把鎖來處理。lock是確保當一個線程位於代碼的臨界區時,另一個線程不進入臨界區。如果其他線程試圖進入鎖定的代碼,則它將一直等待(即被阻止),直到該對象被釋放。
public class Singleton { private static Singleton instance; private static readonly object synRoot=new object(); private Singleton() //改為私有 { } public static Singleton GetInstance() { lock(synRoot) { if(instance==null) { instance=new Singleton(); } return instance; } } }
雙重鎖定:不用讓線程每次都加鎖,而只是在實例未被創建的時候再加鎖處理,提高了性能。
public class Singleton { private static Singleton instance; private static readonly object synRoot=new object(); private Singleton() //改為私有 { } public static Singleton GetInstance() { if(instance==null) { lock(synRoot) { if(instance==null) { instance=new Singleton(); } return instance; } } } }