Json.NET不区分大小写的属性反序列化

时间:2012-06-29 17:57:21

标签: c# json.net

Json.NET将“不区分大小写的属性反序列化”列为广告功能之一。我已经读过,将首先尝试匹配指定属性的大小写,如果未找到匹配项,则执行不区分大小写的搜索。但是,这似乎不是默认行为。请参阅以下示例:

var result =
    JsonConvert.DeserializeObject<KeyValuePair<int, string>>(
        "{key: 123, value: \"test value\"}"
    );

// result is equal to: default(KeyValuePair<int, string>)

如果改变JSON字符串以匹配属性的情况(“Key”和“Value”vs“key”和“value”),那么一切都很好:

var result =
    JsonConvert.DeserializeObject<KeyValuePair<int, string>>(
        "{Key: 123, Value: \"test value\"}"
    );

// result is equal to: new KeyValuePair<int, string>(123, "test value")

有没有办法执行不区分大小写的反序列化?

3 个答案:

答案 0 :(得分:26)

这是一个错误。

不区分大小写的属性反序列化是指Json.NET能够使用名称&#34; Key&#34;来映射JSON属性。要么是.NET课程,要么是#34; Key&#34;或&#34;关键&#34;构件。

错误是KeyValuePair需要自己的JsonConverter但是错过了不区分大小写的映射。

https://github.com/JamesNK/Newtonsoft.Json/blob/fe200fbaeb5bad3852812db1e964473e1f881d93/Src/Newtonsoft.Json/Converters/KeyValuePairConverter.cs

使用它作为基础并添加小写&#34;键&#34;和&#34;价值&#34;阅读JSON时的case语句。

答案 1 :(得分:8)

我找到的一种有效方法是将GetValue与StringComparer参数一起使用。

例如,

JObject contact;
String strName = contact.GetValue('Name');

您尝试将“名称”属性设置为不区分大小写,您可以使用

JObject contact;
String strName = contact.GetValue("ObjType", StringComparison.InvariantCultureIgnoreCase);

答案 2 :(得分:0)

您可以在传入属性名称上使用自定义合同解析器,可以将传入属性更改为与C#对象类属性格式匹配的首选格式。我制作了三个自定义合同解析器,它将传入的属性名称更改为“标题” /“小写” /“大写”:

public class TitleCaseContractResolver : DefaultContractResolver
{
    protected override string ResolvePropertyName(string propertyName)
    {
        //Change the incoming property name into Title case
        var name = string.Concat(propertyName[0].ToString().ToUpper(), propertyName.Substring(1).ToLower());
        return base.ResolvePropertyName(name);
    }
}

public class LowerCaseContractResolver : DefaultContractResolver
{
    protected override string ResolvePropertyName(string propertyName)
    {
        //Change the incoming property name into Lower case
        return base.ResolvePropertyName(propertyName.ToLower());
    }
}

public class UpperCaseContractResolver : DefaultContractResolver
{
    protected override string ResolvePropertyName(string propertyName)
    {
        //Change the incoming property name into Upper case
        return base.ResolvePropertyName(propertyName.ToUpper());
    }
}

然后创建一个新的JsonSerializerSetting对象,并将您的自定义合同解析器放入属性ContractResolver中。然后将JsonSerializerSetting对象添加到JsonConvert.DeserializeObject(jsonString,jsonSerializerSetting)的第二个参数中

        var serializerSetting = new JsonSerializerSettings()
        {
            ContractResolver = new TitleCaseContractResolver()
        };
        var result = JsonConvert.DeserializeObject<YourType>(jsonString, serializerSetting);