Newtonsoft Json - 反序列化 - 如果属性名称相同但属性类型不同,则自定义映射

时间:2016-07-01 07:38:09

标签: c# .net rest serialization json.net

我正在调用REST API以将对象作为ResponseData。

CustomField CustomFieldObj = JsonConvert.DeserializeObject<CustomField>(ResponseData.ToString());

//类定义(DataType类型为int?

public class CustomField {
 public int? DataType {get; set;}
}

API有这样的对象(DataType类型为string

public class ResposeData {
     public string DataType {get; set;}
    }

现在,JsonConvert.DeserializeObject因为数据类型不同而抛出错误(字符串无法转换为int)。
那么,在反序列化时如何忽略具有不同数据类型的这些属性?

1 个答案:

答案 0 :(得分:0)

复杂的答案是您可以指定要在反序列化过程中使用的转换器:JsonConverter

基础知识是,您可以使用JsonConverter作为基类并覆盖这些属性:

public class KeysJsonConverter : JsonConverter
{
    private readonly Type[] _types;

    public KeysJsonConverter(params Type[] types)
    {
        _types = types;
    }

    public override void WriteJson(JsonWriter writer, object value, JsonSerializer serializer)
    {
        JToken t = JToken.FromObject(value);

        if (t.Type != JTokenType.Object)
        {
            t.WriteTo(writer);
        }
        else
        {
            JObject o = (JObject)t;
            IList<string> propertyNames = o.Properties().Select(p => p.Name).ToList();

            o.AddFirst(new JProperty("Keys", new JArray(propertyNames)));

            o.WriteTo(writer);
        }
    }

    public override object ReadJson(JsonReader reader, Type objectType, object existingValue, JsonSerializer serializer)
    {
        throw new NotImplementedException("Unnecessary because CanRead is false. The type will skip the converter.");
    }

    public override bool CanRead
    {
        get { return false; }
    }

    public override bool CanConvert(Type objectType)
    {
        return _types.Any(t => t == objectType);
    }
}

这是James Newton-King的extract

如果您希望将JSON读入对象,那么您将要覆盖ReadJsonCanRead方法。

如果您希望指定此转换器可以读取json,请覆盖CanRead方法并返回true。

然后,您需要覆盖ReadJson方法才能读取值。

source code for other converters会帮助您了解如何实施ReadJson,但请注意您将使用反射。