将json反序列化为具有默认私有构造函数的类的C#对象
我需要将json反序列化为以下类。
public class Test { public string Property { get; set; } private Test() { //NOTHING TO INITIALIZE } public Test(string prop) { Property = prop; } }
我可以创建一个Test实例
var instance = new Test("Instance");
考虑我的json之类的东西
"{ "Property":"Instance" }"
我如何创建Test类的对象,因为我的默认构造函数是私有的,我得到的对象是Property为NULL
我正在使用Newtonsoft Json解析器。
您可以通过使用[JsonConstructor]
属性标记Json.Net来调用私有构造函数:
[JsonConstructor] private Test() { //NOTHING TO INITIALIZE }
请注意,在调用构造函数后,序列化程序仍将使用公共setter填充对象。
编辑
另一种可能的选择是使用ConstructorHandling
设置:
JsonSerializerSettings settings = new JsonSerializerSettings { ConstructorHandling = ConstructorHandling.AllowNonPublicDefaultConstructor }; Test t = JsonConvert.DeserializeObject(json, settings);
您似乎不需要采取任何额外步骤。
使用Json.NET v6.0.8,以下C#程序在LINQPad中运行:
void Main() { var o = JsonConvert.DeserializeObject("{\"Property\":\"Instance\"}"); Debug.Assert(o.Property == "Instance", "Property value not set when deserializing."); } public class Test { public string Property { get; set; } private Test() { } public Test(string propertyValue) { Property = propertyValue; } }
无需创建Serializer设置并在此处指定ConstructorHandling。 请记住将[JsonConstructor]
属性定义为私有构造函数。 我有类似的抽象BaseNode.cs案例及其具体的ComputerNode.cs实现。 您可以创建类,复制/粘贴下面的代码并进行一些实验。
public abstract class BaseNode { [JsonConstructor] // ctor used when Json Deserializing protected BaseNode(string Owner, string Name, string Identifier) { this.Name = Name; this.Identifier = Identifier; } // ctor called by concrete class. protected BaseNode(string [] specifications) { if (specifications == null) { throw new ArgumentNullException(); } if (specifications.Length == 0) { throw new ArgumentException(); } Name = specifications[0]; Identifier = specifications[1]; } public string Name{ get; protected set; } public string Identifier { get; protected set; } } public class ComputerNode: BaseNode { public string Owner { get; private set; } [JsonConstructor] // not visible while creating object from outside and only used during Json Deserialization. private ComputerNode(string Owner, string Name, string Identifier):base(Owner, Name, Identifier) { this.Owner = Owner; } public ComputerNode(string[] specifications):base(specifications) { Owner = specifications[2]; } }
对于JSon读写以下代码有帮助 –
public class Operation { public string path; public Operation() { var path = Path.Combine(Directory.GetCurrentDirectory(), "nodes.txt"); if (File.Exists(path) == false) { using (File.Create(path)) { } } this.path = path; } public void Write(string path, List nodes) { var ser = JsonConvert.SerializeObject(nodes, Formatting.Indented); File.WriteAllText(path, ser); } public List Read(string path) { var text = File.ReadAllText(path); var res = JsonConvert.DeserializeObject>(text); return res; } }
祝一切顺利!