Cap*_*mic 13 .net c# multithreading locking
请考虑以下函数,该函数仅实现对一个线程的非阻塞访问.
public bool TryCancelGroup()
{
if (Monitor.TryEnter(_locked))
{
if (_locked == false)
{
_locked = true;
try
{
// do something
}
catch (Exception ex)
{
_locked = false;
}
finally
{
Monitor.Exit(_locked);
}
}
return _locked;
}
else
{
return false;
}
}
Run Code Online (Sandbox Code Playgroud)
这是_locked变量的定义方式.
bool _locked = false;
Run Code Online (Sandbox Code Playgroud)
现在,当程序到达时,Monitor.Exit(_locked);它会抛出一个System.Threading.SynchronizationLockException说明_locked变量之前未同步的说法.
当_locked变量被定义为对象之前,这一切都在起作用
object _locked = new object();
Run Code Online (Sandbox Code Playgroud)
当我将它更改为bool以便将其用作布尔标志时,我开始得到此异常.
Jar*_*Par 27
原因是Monitor方法都采用System.Object参数.当你传入bool一个盒子需要转换为Object.框操作System.Object为每个调用生成一个新值.因此,TryEnter和Exit方法看到不同的对象并导致异常.
当_locked被输入到Object没有必要为一个盒子.因此,TryEnter和Exit方法看到相同的对象,并且可以正常运行.
关于代码的一些其他评论
_locked变量仅false在异常情况下设置.如果执行没有产生异常,它将保持为真,并且没有线程将再次进入该if块. 小智 5
将监视器上的超时设置为0有助于实现所需的行为.使用全局声明的对象来锁定.
static object mylock = new object();
Run Code Online (Sandbox Code Playgroud)
....
if (Monitor.TryEnter(mylock, 0))
{
try
{
// Do work
}
finally
{
Monitor.Exit(mylock);
}
}
Run Code Online (Sandbox Code Playgroud)