c# - 使用 newtonsoft.json 反序列化 List<AbstractClass>

标签 c# .net vb.net serialization json.net

我正在尝试序列化和反序列化 abstract 类列表(mustinherit for vb),显然其中只有派生类的实例。

我用 JsonProperty(ItemTypeNameHandling = TypeNameHandling.Auto) 修饰了列表参数,获得如下所示的输出:

但是我反序列化的时候一直说他不能反序列化一个抽象类。

http://james.newtonking.com/json/help/index.html?topic=html/SerializeTypeNameHandling.htm

public class ConcreteClass
{
    private ObservableCollection<AbstractClass> _Nodes = new ObservableCollection<AbstractClass>();
    //<Newtonsoft.Json.JsonProperty(itemtypenamehandling:=Newtonsoft.Json.TypeNameHandling.Auto)>
    public ObservableCollection<AbstractClass> Nodes {
        get { return this._Nodes; }
    }
    public string Name { get; set; }
    public int Id { get; set; }
}

public abstract class AbstractClass
{
    private ObservableCollection<AbstractClass> _Nodes = new ObservableCollection<AbstractClass>();
    [Newtonsoft.Json.JsonProperty(itemtypenamehandling = Newtonsoft.Json.TypeNameHandling.Auto)]
    public ObservableCollection<AbstractClass> Nodes {
        get { return this._Nodes; }
    }
}

删除注释行就可以了!

最佳答案

确保在反序列化时指定 TypeNameHandling,按照文档:

// for security TypeNameHandling is required when deserializing
Stockholder newStockholder = JsonConvert.DeserializeObject<Stockholder>(jsonTypeNameAuto, new JsonSerializerSettings
{
    TypeNameHandling = TypeNameHandling.Auto
});

值得注意的是,文档正在反序列化一个包含抽象类集合的具体类。

作为实验,尝试创建一个一次性类(具体),该类具有单个属性以及您的抽象对象列表,看看您是否可以对其进行序列化和反序列化。

更新:

我刚刚在 LINQPad 中测试了以下代码:

void Main()
{
    var test = new List<Business>();
    test.Add(new Hotel { Name = "Hilton", Stars = 5 });
    test.Add(new Pool { Name = "Big Splash", Capacity = 500 });

    test.Dump();

    string json = JsonConvert.SerializeObject(test, Newtonsoft.Json.Formatting.Indented, new JsonSerializerSettings
    {
        TypeNameHandling = TypeNameHandling.All
    });

    json.Dump();

    var businesses = JsonConvert.DeserializeObject<List<Business>>(json, new JsonSerializerSettings
    {
        TypeNameHandling = TypeNameHandling.All
    });

    businesses.Dump();
}

// Define other methods and classes here
public abstract class Business
{
    public string Name { get;set; }
}
public class Hotel : Business
{
    public int Stars { get;set; }
}
public class Pool : Business
{
    public int Capacity { get;set;}
}

它工作得很好。摘要集合序列化为:

{
  "$type": "System.Collections.Generic.List`1[[UserQuery+Business, query_jvrdcu]], mscorlib",
  "$values": [
    {
      "$type": "UserQuery+Hotel, query_jvrdcu",
      "Stars": 5,
      "Name": "Hilton"
    },
    {
      "$type": "UserQuery+Pool, query_jvrdcu",
      "Capacity": 500,
      "Name": "Big Splash"
    }
  ]
}

原始集合和反序列化集合匹配。

关于c# - 使用 newtonsoft.json 反序列化 List<AbstractClass>,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/20038441/

相关文章:

c# - 使用索引 C# 返回数组的子集

c# - 如何使用 .net 读取包含 2900 万行数据的巨大 CSV 文件

.net - 为 mac 编写 .net 软件

vb.net - VB中 "Public Shared"子/函数的含义

c# - 如何在时间流逝时收集按键?

c# - SSLStream 读取无效数据 + KB3147458 SSLStream 错误(?)

c# - 隐藏表单时,Form.Invoke() 不会运行,

c# - 如何设置可用于 ResourceDictionary 中背景属性的原色

asp.net - 防止数字以指数表示法显示的更简单方法

vb.net - VB 中的类与模块