2010-04-19 32 views
2

考慮以下兩種情況:C# - 哪個更高效且線程安全?靜態或即時課程?

//Data Contract 
public class MyValue 
{ 
} 

方案1:使用靜態輔助類。

public class Broker 
{ 
    private string[] _userRoles; 

    public Broker(string[] userRoles) 
    { 
     this._userRoles = userRoles; 
    } 

    public MyValue[] GetValues() 
    { 
     return BrokerHelper.GetValues(this._userRoles); 
    } 
} 

static class BrokerHelper 
{ 
    static Dictionary<string, MyValue> _values = new Dictionary<string, MyValue>(); 
    public static MyValue[] GetValues(string[] rolesAllowed) 
    { 
     return FilterForRoles(_values, rolesAllowed); 
    } 
} 

方案2:使用一個實例類。

public class Broker 
{ 
    private BrokerService _service; 

    public Broker(params string[] userRoles) 
    { 
     this._service = new BrokerService(userRoles); 
    } 

    public MyValue[] GetValues() 
    { 
     return _service.GetValues(); 
    } 
} 

class BrokerService 
{ 
    private Dictionary<string, MyValue> _values; 
    private string[] _userRoles; 

    public BrokerService(string[] userRoles) 
    { 
     this._userRoles = userRoles; 
     this._values = new Dictionary<string, MyValue>(); 
    } 

    public MyValue[] GetValues() 
    { 
     return FilterForRoles(_values, _userRoles); 
    } 
} 

哪[經紀人]方案將如果在一個網絡環境中約100個不同的角色和超過一千用戶使用最佳尺度。

注:隨意採取任何替代方法。

回答

5

您可以使用靜態或實例類來搞定線程。但是,正確獲取線程的關鍵是確保兩個線程不會同時嘗試訪問相同的資源。

對於靜態類,根據定義,它只有一個副本,因此所有線程都需要很好地共享。

通過實例類,您可以爲每個線程創建一個實例。如果確保每個線程只訪問它自己的實例,並且實例屬性和方法不會反過來訪問其他共享資源,則它們應該是線程安全的。

在你的情況,我沒有看到任何東西在初始化後在類中被改變。如果你確保以線程安全的方式初始化你的靜態類(這裏似乎是這種情況),靜態變量應該是線程安全的(因爲只讀訪問變量),並且會更快一些,因爲你沒有創建和處理實例的開銷。

2

這兩種方法都有它們自己的問題。我通常的做法是去實例類(因爲它們也更容易測試),但是如果你想要每線程數據,你可以定義該類的靜態實例。無論如何,如果您的數據將被共享,您可能需要investigate the ReaderWriterLockSlim class

1

實例類會更安全,因爲每個線程每個線程可以有一個副本,另一方面,靜態類只能有一個,所以如果您需要線程共享數據,請確保實現某種鎖定機制這樣他們可以很好地相處。 還指定您需要速度或資源消耗的效率的上下文。

+0

他似乎沒有在初始化後編寫任何數據。 – 2010-04-19 16:35:10

0

沒有絕對的線程安全選擇,如果你不打算訪問共享數據,沒有區別,如果你是,仍然沒有區別,但靜態類更可能使用共享數據,因爲它們是靜態的,幾乎所有的東西都是共享的。所以使用即時課程。作爲Martin Fowler的Singleton模式,即使你想要靜態的東西,最好使它成爲單例模式,因爲它更加靈活。