2012-10-22 19 views
1

有很多帖子說SingleInstance是一個糟糕的設計。但我認爲這是我的情況的最佳選擇。
在我的服務中,我必須返回當前登錄用戶的列表(附加數據)。該列表對於所有客戶都是相同的。我想每5秒鐘從數據庫中檢索這個列表(例如),並在需要時將其副本返回給客戶端。
如果我使用PerCall實例化模式,我會每次從數據庫檢索這個列表。這份清單應該包含200-500條記錄,但將來可能會增長到10000條記錄。每個記錄都很複雜,包含大約10個字段。WCF中的單實例VS PerCall

那麼性能呢?使用「糟糕的設計」並獲取一次列表或在每次調用中使用「好方法」並從數據庫獲取列表更好嗎?

回答

2

那麼性能呢?使用「不好的設計」並獲得 列表一次或使用「好方法」並從每個電話的 數據庫獲取列表更好嗎?

性能和優秀的設計不互相排斥。使用單個實例的問題是它一次只能處理一個請求。所有其他請求都在等待它完成它的事情。

或者,您可以利用caching layer來保存查詢的結果,而不是將其耦合到您的服務。

然後你的代碼可能是這個樣子:

public IEnumerable<BigDataRecord> GetBigExpensiveQuery(){ 

    //Double checked locking pattern is necessary to prevent 
    // filling the cache multiple times in a multi-threaded 
    // environment 
    if(Cache["BigQuery"] == null){ 
     lock(_bigQueryLock){ 
     if(Cache["BigQuery"] == null){ 
      var data = DoBigQuery(); 
      Cache.AddCacheItem(data, TimeSpan.FromSeconds(5)); 
     } 
     } 
    } 

    return Cache["BigQuery"]; 

} 

現在,只要你想都訪問相同的緩存可以有多個實例。

+1

您可以將ConcurrencyMode設置爲多個usingInstanceContextMode單一,在同一個實例上同時處理多個請求 – Soulbe

+1

@Soulbe - 但我假設他打算將數據保存在內存中。這意味着現在他必須確保他的服務實例也是線程安全的。爲什麼要經過所有的努力才能使用已經線程安全的'System.Runtime.Caching'? – Josh

+0

事實上,我正在考慮在多個併發模式下使用單實例:S但是您的解決方案將使我的工作變得更容易。我沒有得到的東西:所有實例將共享相同的緩存?我怎麼能通過定時器更新來自數據庫的緩存值? – ChruS