C#同步集合的最佳实践
鉴于以下情况,最好的同步技术人员是什么 *请注意,这是一个示例模型,还有更多的事情要做。 共享资源是仪器字典,它从两个地方更新: (1) 内部值正在快速更新 (2) 整个集合将刷新C#同步集合的最佳实践,c#,multithreading,asynchronous,C#,Multithreading,Asynchronous,鉴于以下情况,最好的同步技术人员是什么 *请注意,这是一个示例模型,还有更多的事情要做。 共享资源是仪器字典,它从两个地方更新: (1) 内部值正在快速更新 (2) 整个集合将刷新 public class Insturment { public Feed Feed{ get; set;} } static IDictionary<string,Instrument> instruments = new Dictionary<string,Ins
public class Insturment
{
public Feed Feed{ get; set;}
}
static IDictionary<string,Instrument> instruments = new Dictionary<string,Instrument>();
// (1) This happens frequently
public void OnNewFeed(Feed feed)
{
instruments[feed.Symbol].Feed = feed;
}
// (2) happens every few hours ,or manually triggered at any given time
public void BuildInstruments()
{
foreach(var instrument in newInstruments)
{
instruments.AddOrUpdate(insturment.Symbol,insturment);
}
}
或者使用任何类型的任务包装器并等待它。
类似这样的构造:
- 旁注:阅读字典时,我不关心数据的完整性。这意味着我不介意有人在任何给定点从字典接收未更新的值。我真的很介意实际更新永远丢失,因为我刚刚更换了正在更新的整个仪器李>
lock
,除非您需要其他东西
例如,如果需要异步锁定,可以使用SemaphoreSlim
或asynchlock
实现之一
或者使用任何类型的任务包装器并等待它
我不会将该解决方案用于集合同步。如果需要异步兼容的同步,请使用异步兼容的同步原语(例如SemaphoreSlim
或AsyncLock
)。如果您不需要它,那么只需使用lock
只有当您必须使用基于WaitHandle
的对象(例如,它在进程之间共享)并希望使用异步代码时,才真正需要使用Task
-wrapper-around-WaitHandle
情况。听起来这种情况在这里并不适用
旁注:阅读字典时,我不关心数据的完整性。这意味着我不介意有人在任何给定点从字典接收未更新的值
无论如何,我建议锁定读取。如果不这样做,可能会出现各种各样的问题(比如撕裂)
作为旁注:您对场景的描述一直使用术语“更新”。听起来你可能更想要一个生产者/消费者解决方案,或者像Rx一样发布/订阅,而不是一个共享的同步集合。使用ConcurrentDictionarylets说我是,请描述一下这对我有什么帮助。我很高兴你提起了这件事请注意,我正在替换Build()中的整个instrument对象,我不想在替换字典中的父对象时丢失新的提要。对不起,我误解了你的问题,忘了它:),除非你希望有来自不同来源的多个OnNewFeed,否则它不会帮助你,对不起,弄错了。
ManualResetEvent _mre = new ManualResetEvent(false);
public void OnNewFeed(Feed feed)
{
_mre.WaitOne();
instruments[feed.Symbol].Feed = feed;
}
public void BuildInstruments()
{
_mre.Reset();
foreach(var instrument in newInstruments)
{
instruments.AddOrUpdate(insturment.Symbol,insturment);
}
_mre.Set();
}