C# 防止线程不必要地执行代价高昂的任务
我希望通过以下方式保护对资源的访问:C# 防止线程不必要地执行代价高昂的任务,c#,multithreading,concurrency,locking,C#,Multithreading,Concurrency,Locking,我希望通过以下方式保护对资源的访问: 除了在更新期间(如果更新不是原子的),所有线程都可以并发读取 只有一个线程可以被分配更新任务,直到下一次 需要更新 这可能看起来像是一个简单的问题,即使用适当的锁,或者可能使所有操作原子化,但我认为这不是问题所在 如果我只是有一个用于更新的写锁(即ReaderWriterLockSlim),或者使用非锁定代码,那么没有什么可以阻止多个线程运行更新过程(或者排队执行)。如果我在检查资源是否需要更新之前使用锁定来阻止线程,那么它们不能并发执行,但可以有效地序
- 除了在更新期间(如果更新不是原子的),所有线程都可以并发读取
- 只有一个线程可以被分配更新任务,直到下一次 需要更新
锁,或者可能使所有操作原子化,但我认为这不是问题所在
如果我只是有一个用于更新的写锁(即ReaderWriterLockSlim
),或者使用非锁定代码,那么没有什么可以阻止多个线程运行更新过程(或者排队执行)。如果我在检查资源是否需要更新之前使用锁定来阻止线程,那么它们不能并发执行,但可以有效地序列化
我可以让特定的线程执行资源的所有检查和更新,并利用类似于ManualResetEvent
的方法将其他读取线程搁置,直到更新完成。(或者,如果更新是作为一个原子操作实现的,只需满足于使用特定的更新线程即可。)
然而,我不确定最佳实践,我想问一下您是否认为这些要求可以用更少的努力来满足,或者我的任何假设都有偏差。我想您正在寻找一个
ReaderWriterLockSlim
。使用独占锁定模式进行写入。我知道ReaderWriterLockSlim类,但我无法找到一种使用模式,防止线程排队执行不必要的更新,即使使用独占锁定模式进行写入。这就是我在我的问题中试图解释的——“如果我只是有一个用于更新的写锁[…],没有什么可以阻止多个线程运行更新过程(或排队执行更新过程)”。我忽略了这一点。尝试在零超时的情况下获取写锁,并在锁忙的情况下跳过更新。我明白你的想法,但该线程仍然需要返回一个值。因此,我需要返回并重试,可能会多次进入“更新模式”,直到“第一个线程”完成对资源的更新。我觉得有点不干净。还是我弄错了?我明白问题所在。将可写资源设为惰性资源。一个编写器可以在写锁下创建一个新的延迟并立即退出。然后,任何先到的线程都会迫使懒惰的线程运行。所有线程在完成时拾取相同的值。有趣。我不会想到使用Lazy
类来实现这一点。我得试一试。请你用一段代码来更新你的答案,这样如果我接受这个答案,其他人可能会更容易理解为什么?奇怪的问题。如果您的线程非常难以控制,以至于您无法在代码中确保只启动执行更新一次的线程,那么您也无法保证它们的行为良好并正确使用RWL。添加额外的锁只会导致死锁。这从来都不是一个真正的问题,不要让它成为一个问题。为什么你会假设对访问实例的线程拥有控制权?请随意解释一下你是如何确定“这从来不是一个真正的问题”的。这似乎是一个奇怪的评论。