它已經一段時間,因爲這個問題問,但我最近碰到了一個類似類型的問題,並最終做低於這個幫助我們滿足性能標準。
你基本上分割你的名單分成塊,並在一個多線程的方式sperate線程中處理它們。每個新線程都會啓動自己的uow,這需要您的實體被連接。
有一點要注意的是你的數據庫需要進行快照隔離被啓用。否則可能會導致死鎖。您需要確定您正在執行的操作和相關業務流程是否正常。在我們的案例中,這是產品實體的簡單更新。
你可能需要做一些測試,以決定最佳的塊大小,也限制了並行所以總有資源完成操作。
private void PersistProductChangesInParallel(List<Product> products,
Action<Product, string> productOperationFunc,
string updatedBy)
{
var productsInChunks = products.ChunkBy(20);
Parallel.ForEach(
productsInChunks,
new ParallelOptions { MaxDegreeOfParallelism = 20 },
productsChunk =>
{
try
{
using (var transactionScope = new TransactionScope(
TransactionScopeOption.Required,
new TransactionOptions { IsolationLevel = IsolationLevel.Snapshot }))
{
var dbContext = dbContextFactory.CreatedbContext();
foreach (var Product in productsChunk)
{
dbContext.products.Attach(Product);
productOperationFunc(Product, updatedBy);
}
dbContext.SaveChanges();
transactionScope.Complete();
}
}
catch (Exception e)
{
Log.Error(e);
throw new ApplicationException("Some products might not be updated", e);
}
});
}
@usr你有更好的主意? – Cocowalla 2013-07-05 10:58:31
@Cocowalla不知道OP正在處理的更大場景,我不知道。他的兩個解決方案都會導致一個痛苦的實施,這就是爲什麼我要警告他。也許他可以採用完全不同的路徑,並以單線程方式使用EF(它的使用方式)。 – usr 2013-07-05 11:56:40
另外一點需要注意的:你不能做任何更改的實體時,它是分離的,因爲沒有上下文目前正在跟蹤這種變化。 SaveChanges()稍後調用時,更改不會保留。 – JoeCool 2015-01-07 16:38:53