我正在尝试编写一种处理某些消息的方法。它们可以被读取或写入消息。允许并行读取,但是当write
获得锁时,所有后续的读锁都应该等到写锁被释放。所以我认为ReaderWriterLockSlim
这是我需要的。但是当我尝试实现简单的应用程序以查看它是否按预期工作时,我得到了Recursive read lock acquisitions not allowed in this mode
异常。
这是我的示例来展示它的工作原理:
ReaderWriterLockSlim distributionLock = new ReaderWriterLockSlim();
async Task ExecuteReadLockTaskAsync(Func<Task> taskFunc)
{
distributionLock.EnterReadLock();
try
{
await taskFunc();
}
finally
{
if (distributionLock.IsReadLockHeld)
{
distributionLock.ExitReadLock();
}
}
}
async Task ExecuteWriteLockTaskAsync(Func<Task> taskFunc)
{
distributionLock.EnterWriteLock();
try
{
await taskFunc();
}
finally
{
if (distributionLock.IsWriteLockHeld)
{
distributionLock.ExitWriteLock();
}
}
}
Task ProcessAsync(bool flag)
{
switch (flag)
{
case false:
return ExecuteReadLockTaskAsync(() =>
{
Console.WriteLine("Readonly task start");
return Task.Delay(1000).ContinueWith(t => Console.WriteLine("Readonly task done"));
});
case true:
return ExecuteWriteLockTaskAsync(() =>
{
Console.WriteLine("Write task start");
return Task.Delay(3000).ContinueWith(t => Console.WriteLine("Write task done"));
});
default:
throw new InvalidOperationException($"Unknown message typex");
}
}
var tasks= new List<Task>();
for (int i = 0; i < 100; i++)
{
tasks.Add(ProcessAsync(false));
}
tasks.Add(ProcessAsync(true));
for (int i = 0; i < 100; i++)
{
tasks.Add(ProcessAsync(false));
}
await Task.WhenAll(tasks);
预期结果: 100 行Readonly task start
, 1 行Write task start
, 然后 100 行Readonly task done
, 然后 1 行Write task done
, 然后程序的其余部分打印。
实际结果:
Readonly task start
Readonly task done
LockRecursionException4
Recursive read lock acquisitions not allowed in this mode.
我不明白递归出现在哪里。我只是调用一个函数,没有任何递归。我阅读了文章,但我看不到它在这里是如何工作的。