gpt4 book ai didi

c# - 调用 MethodInfo.MakeGenericMethod 时出现这个关键错误是什么意思?

转载 作者:太空宇宙 更新时间:2023-11-03 11:25:41 25 4
gpt4 key购买 nike

今天我从一些旧的动态转换代码中得到了这个错误(我更改了最后一行并省略了堆栈跟踪的其余部分):

Item has already been added. 
Key in dictionary:
'Int32 Count[Object](System.Collections.Generic.IEnumerable`1[System.Object])'
Key being added:
'Int32 Count[Object](System.Collections.Generic.IEnumerable`1[System.Object])'
---> System.ArgumentException: Item has already been added.
Key in dictionary:
'Int32 Count[Object](System.Collections.Generic.IEnumerable`1[System.Object])'
Key being added:
'Int32 Count[Object](System.Collections.Generic.IEnumerable`1[System.Object])'
at System.Reflection.CerHashtable`2.Insert(K[] keys, V[] values, Int32& count, K key, V value)
at System.Reflection.CerHashtable`2.Preallocate(Int32 count)
at System.RuntimeType.RuntimeTypeCache.GetGenericMethodInfo(RuntimeMethodHandle genericMethod)
at System.RuntimeType.GetMethodBase(RuntimeTypeHandle reflectedTypeHandle, RuntimeMethodHandle methodHandle)
at System.Reflection.RuntimeMethodInfo.MakeGenericMethod(Type[] methodInstantiation)
at MyNamespace.CommunicationExtensions.BuildMessage[T](T obj)

全类

public static class CommunicationExtensions {
static readonly object lockobj = new object();
public static bool CanBuildMessage<T>(this T obj) where T: class {
return obj != null && (MessageFactory.MessageBuilders.ContainsKey(obj.GetType()));
}
public static string BuildMessage<T>(this T obj) {
lock (lockobj) {
Delegate d;
var type = obj.GetType();

if (MessageFactory.MessageBuilders.TryGetValue(type, out d)) {
var castMethod = typeof(CommunicationExtensions).GetMethod("Cast").MakeGenericMethod(type);
var castedObject = castMethod.Invoke(null, new object[] { obj });

return d.DynamicInvoke(castedObject) as string;
}
}
return null;
}
public static T Cast<T>(object o) {
return (T)o;
}
}

MessageFactory.MessageBuildersDictionary<Type,Func<Type,string>>包含已编译的 lambda 表达式,这些表达式是根据需要延迟构建的,用于将 Message 事件(基于 EventArgs 的简单自动属性类)转换为其他系统中使用的字符串格式。不过我认为这些都不重要。我认为导致此问题的唯一必要代码是:

public static class CastError{
public static void GetCast<T>(this T obj) {
var type = obj.GetType();
var castMethod = typeof(CastError).GetMethod("Cast").MakeGenericMethod(type);
//...
}
public static T Cast<T>(object o) {
return (T)o;
}
}

最佳答案

看起来是框架未能正确锁定 MakeGenericMethod 的内部结构。

当调用 MakeGenericMethod 时,框架应该使用指定的泛型参数创建方法的新版本,或者如果之前使用了相同的泛型参数类型来创建该泛型方法,那么它应该返回以前生成的方法。看起来你遇到了一个边缘情况,在多个线程上调用 MakeGenericMethod 会导致竞争条件,两个线程都认为该方法尚未生成并继续生成它,然后随后发生冲突存储生成的方法以供将来调用。

就是说,在这种情况下,它看起来像是都在锁中,所以我也不完全相信这就是问题所在。

我会将其作为错误提交给 MSFT,除非其他人可以解释这是预期的行为。

关于c# - 调用 MethodInfo.MakeGenericMethod 时出现这个关键错误是什么意思?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/9419464/

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