DataContractJsonSerializer反序列化问题

时间:2018-09-09 15:25:18

标签: c# asp.net asp.net-mvc-4 datacontractjsonserializer

我需要对下面给出的Json数组进行反序列化...。

[
    {
        "GeoType": 1,
        "ID": "2650f7d2-7a5e-4b63-856c-07600fa2a854",
        "Name": "Afghanistan",
        "CapitalCity": null,
        "CountryBoundaries": null,
        "CountryCode": "AF",
        "ISO": "AFG",
        "Parent": {
            "__type": "Region:#MEDEX.Library.Geo",
            "GeoType": 0,
            "ID": "6dc22edb-d711-4253-937f-242b0cd3c011",
            "Name": "Asia",
            "Code": "Asi"
        },
        "RegionID": "6dc22edb-d711-4253-937f-242b0cd3c011"
    },
    {
        "GeoType": 1,
        "ID": "3917c1c8-ee01-4e9b-8622-0fac9e9194ab",
        "Name": "Albania",
        "CapitalCity": null,
        "CountryBoundaries": null,
        "CountryCode": "AL",
        "ISO": "ALB",
        "Parent": {
            "__type": "Region:#MEDEX.Library.Geo",
            "GeoType": 0,
            "ID": "b7ebd500-45e6-4a48-a2ef-f38fe99e7352",
            "Name": "Europe",
            "Code": "Eur"
        },
        "RegionID": "b7ebd500-45e6-4a48-a2ef-f38fe99e7352"
    }
]

我的对象定义是:

[DataContract]
public class Parent1
{
    [DataMember]
    public Dictionary<string, Type> __type { get; set; }
    [DataMember]
    public string ID { get; set; }
    [DataMember]
    public string Name { get; set; }
    [DataMember]
    public string GeoType { get; set; }
    [DataMember]
    public string Code { get; set; }
}

[DataContract]
public class Country
{
    [DataMember]
    public string ID { get; set; }
    [DataMember]
    public string Name { get; set; }
    [DataMember]
    public string GeoType { get; set; }
    [DataMember]
    public Parent1 Parent { get; set; }
    [DataMember]
    public string RegionID { get; set; }
    [DataMember]
    public string CountryCode { get; set; }
    [DataMember]
    public string ISO { get; set; }
}

总是出错:

  

{“ Element':Parent'包含映射到名称'http://schemas.datacontract.org/2004/07/MEDEX.Library.Geo:Region'的类型的数据。解串器不知道任何映射到该名称的类型。如果使用,请考虑使用DataContractResolver DataContractSerializer或将与“ Region”相对应的类型添加到已知类型的列表中,例如,通过使用KnownTypeAttribute属性或将其添加到传递给序列化器的已知类型的列表中。“}

您能建议我任何解决方案吗?我什至不明白此错误的含义。请提出建议。

2 个答案:

答案 0 :(得分:0)

将[KnownType(Region)]添加到class Parent1属性中

答案 1 :(得分:0)

this answer parse.com: SerializationException deserializing JSON objects with "__type" property 中所述,您的问题是"__type"是{{1 }}。它用于标识多态类型的派生类型。来自docs

  

保留类型信息

     

要保留类型标识,当将复杂类型序列化为JSON时,可以添加“类型提示”,并且反序列化器会识别该提示并采取适当的措施。 “类型提示”是密钥名称为“ __type”的JSON键/值对(两个下划线,后跟单词“ type”)。该值是格式为“ DataContractName:DataContractNamespace”的JSON字符串(名称中第一个冒号之前的任何内容)...

     

类型提示与XML Schema Instance标准定义的xsi:type属性非常相似,并在对XML进行序列化/反序列化时使用。

     

由于与类型提示的潜在冲突,因此禁止使用名为“ __type”的数据成员。

因此,您不能手动将此属性添加到您的类中,并使其正确翻译。

但是,您可以通过定义DataContractJsonSerializer类继承的区域的类层次结构,利用序列化程序对多态性的处理来自动读写"__type" Region所引用的某种基本类型,例如RegionBase

Country.Parent

然后将其反序列化为[DataContract(Namespace = "http://schemas.datacontract.org/2004/07/MEDEX.Library.Geo")] public class Country { [DataMember] public string ID { get; set; } [DataMember] public string Name { get; set; } [DataMember] public string GeoType { get; set; } [DataMember] public RegionBase Parent { get; set; } [DataMember] public string RegionID { get; set; } [DataMember] public string CountryCode { get; set; } [DataMember] public string ISO { get; set; } } [DataContract(Namespace = "http://schemas.datacontract.org/2004/07/MEDEX.Library.Geo")] [KnownType(typeof(Region))] public class RegionBase { } [DataContract( Name = "Region", Namespace = "http://schemas.datacontract.org/2004/07/MEDEX.Library.Geo")] public class Region : RegionBase { [DataMember] public string ID { get; set; } [DataMember] public string Name { get; set; } [DataMember] public string GeoType { get; set; } [DataMember] public string Code { get; set; } } ,因为您的外部JSON容器是一个数组。

注意: