首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >多级锁?

多级锁?
EN

Stack Overflow用户
提问于 2018-11-16 13:18:41
回答 2查看 88关注 0票数 1

在并行处理方面,我有一个Parallel.For循环,它在可枚举的情况下进行查找,如果找不到它要查找的内容,就添加它。但是,我经常遇到这样的问题:一个线程修改枚举,而另一个线程正在查找,这使得它抛出了一个异常。显而易见的解决方案是在查找和输入时都使用lock,但这有点蛮力。我希望它能够运行多个并发查找,因此我不希望在一个线程执行查找时完全锁定它,但我确实希望在查找过程中阻止它执行添加。有办法做这样的两级锁吗?

EN

回答 2

Stack Overflow用户

回答已采纳

发布于 2018-11-16 13:29:04

您可能需要使用ReaderWriterLock

代码语言:javascript
复制
private ReaderWriterLockSlim lock = new ReaderWriterLockSlim();

public string Read () {
    lock.EnterReadLock ();
    try {
        return "xxx";
    } finally {
        lock.ExitReadLock();
    }
}

public void Write () {
    lock.EnterWriteLock ();
    try {
        // ...
    } finally {
        lock.ExiteWriteLock ();
    }
}

多个线程可能拥有ReaderWriterLock的“读取器”部分,但只有一个线程可以拥有“编写器”部分(并且在有作者时不可能有读取器)。

票数 4
EN

Stack Overflow用户

发布于 2018-11-16 13:23:46

我会考虑使用某种形式的不可变集合和Interlocked来替换共享实例。

例如,你提到了“查找”,那么ImmutableDictionary可能是一个很好的匹配吗?

然后,对于查找和更新,您有如下内容:

代码语言:javascript
复制
var local = sharedReference;
while(!local.ContainsKey(lookupValue))
{
    var newValue = /* Whatever */
    var newLocal = local.Add(lookupValue,newValue);
    var result = Interlocked.CompareExchange(ref sharedReference, newLocal, local);
    if(result == local) break;
    local = result;
}
//At this point, local definitely contains a key for lookupValue
票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/53338703

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档