gpt4 book ai didi

c# - 使用字符串作为锁定对象是否可以?

转载 作者:IT王子 更新时间:2023-10-29 03:55:37 26 4
gpt4 key购买 nike

我需要根据一组有限的字符串在一个区域中创建一个临界区。我希望为同一个字符串实例共享锁(有点类似于 String.Intern 方法)。

我正在考虑以下实现:

public class Foo
{
private readonly string _s;
private static readonly HashSet<string> _locks = new HashSet<string>();

public Foo(string s)
{
_s = s;
_locks.Add(s);
}

public void LockMethod()
{
lock(_locks.Single(l => l == _s))
{
...
}
}
}

这种方法有什么问题吗?以这种方式锁定字符串对象是否可以,使用 HashSet<string> 是否存在任何线程安全问题? ?

例如,创建一个 Dictionary<string, object> 是否更好?为每个字符串实例创建一个新的锁对象?


最终实现

根据我的建议,我进行了以下实现:

public class Foo
{
private readonly string _s;
private static readonly ConcurrentDictionary<string, object> _locks = new ConcurrentDictionary<string, object>();

public Foo(string s)
{
_s = s;
}

public void LockMethod()
{
lock(_locks.GetOrAdd(_s, _ => new object()))
{
...
}
}
}

最佳答案

不鼓励锁定字符串,主要原因是(由于字符串驻留)一些其他代码可能在您不知道的情况下锁定同一个字符串实例。造成死锁情况的可能性。

现在,在大多数具体情况下,这可能是一个牵强附会的场景。这更像是图书馆的一般规则。

但另一方面,字符串的明显好处是什么?

所以,一点对一点:

Are there any problems with this approach?

是的,但主要是理论上的。

Is it OK to lock on a string object in this way, and are there any thread safety issues in using the HashSet?

HashSet<>只要线程只并发读取,就不涉及线程安全。

Is it better to, for example, create a Dictionary that creates a new lock object for each string instance?

是的。只是为了安全起见。在大型系统中,避免死锁的主要目的是尽可能将锁定对象保持在本地和私有(private)状态。只有有限数量的代码应该能够访问它们。

关于c# - 使用字符串作为锁定对象是否可以?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/12804879/

26 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com