【发布时间】:2017-01-31 19:27:46
【问题描述】:
我在 WCF 服务调用中有这个方法,它检查 Dictionary,如果没有密钥,则添加到它。我在一个锁块内创建了一个Delegate,想知道这会不会有问题。
if (_delegates.ContainsKey(req.OperationName))
{
return _delegates[req.OperationName](req);
}
else
{
lock (_syncRoot)
{
if (_delegates.ContainsKey(req.OperationName) == false)
{
System.Reflection.MethodInfo mi = GetType().GetMethod(req.OperationName, new Type[] { typeof(DataRequestContext) });
if (mi != null)
{
InvokeDelegate d = new InvokeDelegate((r) => { return mi.Invoke(this, new object[] { r }); });
_delegates.Add(req.OperationName, d);
}
else
{
throw new Exception("Unsupported operation: " + req.OperationName);
}
}
return _delegates[req.OperationName](req);
}
上面的代码是这样执行的:
var del = GetDelegate( request);
del(request);
第一次调用会添加到字典中,后续调用不需要添加到静态字典中,但每次运行代码时都会执行Delegate。
我的大脑说这段代码不会阻塞,对吗?
InvokeDelegate d = new InvokeDelegate((r) => { return mi.Invoke(this, new object[] { r }); });
我无法测试它并生成锁定条件,所以我需要问:
在现实世界场景中实际执行的代码如下,参数req是一个包含我用来执行的运行时值的对象:
public AES.Cloud.Common.DataDictionary GetConditionAndItems(AES.Cloud.Common.DataRequestContext req)
{
List<ConditionItem> items = null;
List<MiscItem> miscitems = null;
var cond = GetConditionAndItems(req.GetValue<Guid>("conditionId"), out items, out miscitems);
AES.Cloud.Common.DataDictionary dd = new Common.DataDictionary();
dd.AddList("items", items);
dd.AddList("miscItems", miscitems);
dd.AddObject("Condition", cond);
return dd;
}
【问题讨论】:
-
我没有看到任何证据表明您在这里处理的线程不止一个……那它为什么会锁定?
-
因为每次执行我的 WCF 服务时都会调用它。
-
您完全没有提到这里涉及 WCF。你认为我们会这样推断吗?
-
真的很重要吗?多个线程将执行此代码,仅此而已。
-
当然这很重要...您没有(现在仍然没有)展示如何以及即使多个线程正在运行此代码。您需要创建一个minimal reproducible example。
标签: c# multithreading delegates locking