使用反射在C#中进行Json的反序列化

6

我想使用反射以及Newtonsoft.Json库的以下方法:

MyType object = JsonConvert.DeserializeObject<MyType>(jsonString);

这是我的一种方法,但它不能正常工作(出现歧义匹配异常):

Type type = Type.GetType("MyType",false);
Type JSONCovert = typeof(JsonConvert);
MethodInfo deserializer = JSONCovert.GetMethod("DeserializeObject", new Type[] { typeof(String) });
deserializer = deserializer.MakeGenericMethod(type);
var o = deserializer.Invoke(null, new object[] { JsonString });

请提供完整的异常细节。 - CSharpie
你在问什么?因为现在不清楚你期望什么。 - Jakub Jankowski
MyType是什么,jsonString长什么样? - L.B
这个答案对我有用,因为我有很多模型,无法为它们编写 switch case 语句,所以我决定使用反射进行反序列化。 - Hesam Kashefi
2
为什么不使用非泛型版本的DeserializeObject呢?object o = JsonConvert.DeserializeObject(JsonString, Type.GetType("MyType")); - Brian Rogers
@BrianRogers 非常感谢,我不知道那个重载! - Hesam Kashefi
1个回答

13
您会收到“模糊匹配异常”,因为在JsonConvert中有两个方法与您提供的名称和参数类型匹配。它们是:
  • public static object DeserializeObject(string value)
  • public static T DeserializeObject<T>(string value)
您需要更加具体地选择正确的方法。不幸的是,您将无法使用GetMethod来实现 - 相反,您需要扫描方法列表并找到正确的方法。您可以这样做:
    var JSONCovert = typeof(JsonConvert);
    var parameterTypes = new[] { typeof(string) };
    var deserializer = JSONCovert.GetMethods(BindingFlags.Public | BindingFlags.Static)
        .Where(i => i.Name.Equals("DeserializeObject", StringComparison.InvariantCulture))
        .Where(i => i.IsGenericMethod)
        .Where(i => i.GetParameters().Select(a => a.ParameterType).SequenceEqual(parameterTypes))
        .Single();

编辑:我可以再澄清一件事情,那就是请记住你的方法将会导致 o 的类型为 object。你无法在编译时将其转换为 MyType


好奇为什么有人踩了这个回答,因为它是正确的。如果有人评论了他们发现的错误或无用之处,那将非常有用。 - kiziu
@kiziu 因为他们渴望有一天能够说:“我们应该成为版主,因为我们标记了这么多帖子...” - 你的回答对其他所有人都是完美的... 在许多地方,人们已经放弃了... 你是第一个把所有条件和过滤器都放在一个特定的位置... 谢谢你。 - Hassan Faghihi

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接