And*_*ell 63 c# serialization json json.net deserialization
我试图移动一些代码来使用ASP.NET MVC Web API生成的Json数据而不是SOAP Xml.
我遇到了序列化和反序列化类型属性的问题:
IEnumerable<ISomeInterface>.
Run Code Online (Sandbox Code Playgroud)
这是一个简单的例子:
public interface ISample{
int SampleId { get; set; }
}
public class Sample : ISample{
public int SampleId { get; set; }
}
public class SampleGroup{
public int GroupId { get; set; }
public IEnumerable<ISample> Samples { get; set; }
}
}
Run Code Online (Sandbox Code Playgroud)
我可以使用以下命令轻松序列化SampleGroup的实例:
var sz = JsonConvert.SerializeObject( sampleGroupInstance );
Run Code Online (Sandbox Code Playgroud)
但是相应的反序列化失败:
JsonConvert.DeserializeObject<SampleGroup>( sz );
Run Code Online (Sandbox Code Playgroud)
使用此异常消息:
"无法创建JsonSerializationExample.ISample类型的实例.Type是接口或抽象类,无法立即显示."
如果我派生出一个JsonConverter,我可以按如下方式装饰我的属性:
[JsonConverter( typeof (SamplesJsonConverter) )]
public IEnumerable<ISample> Samples { get; set; }
Run Code Online (Sandbox Code Playgroud)
这是JsonConverter:
public class SamplesJsonConverter : JsonConverter{
public override bool CanConvert( Type objectType ){
return ( objectType == typeof (IEnumerable<ISample>) );
}
public override object ReadJson( JsonReader reader, Type objectType, object existingValue, JsonSerializer serializer ){
var jA = JArray.Load( reader );
return jA.Select( jl => serializer.Deserialize<Sample>( new JTokenReader( jl ) ) ).Cast<ISample>( ).ToList( );
}
public override void WriteJson( JsonWriter writer, object value, JsonSerializer serializer ){
... What works here?
}
}
Run Code Online (Sandbox Code Playgroud)
这个转换器解决了反序列化问题,但我无法想象如何编写WriteJson方法以使序列化再次工作.
有人可以帮忙吗?
这首先是解决问题的"正确"方法吗?
cuo*_*gle 66
你不需要使用JsonConverterAttribute,保持你的模型干净,也使用CustomCreationConverter,代码更简单:
public class SampleConverter : CustomCreationConverter<ISample>
{
public override ISample Create(Type objectType)
{
return new Sample();
}
}
Run Code Online (Sandbox Code Playgroud)
然后:
var sz = JsonConvert.SerializeObject( sampleGroupInstance );
JsonConvert.DeserializeObject<SampleGroup>( sz, new SampleConverter());
Run Code Online (Sandbox Code Playgroud)
文档:使用CustomCreationConverter反序列化
小智 18
它非常简单,并且由json.net提供开箱即用的支持,您只需在序列化和反序列化时使用以下JsonSettings:
JsonConvert.SerializeObject(graph,Formatting.None, new JsonSerializerSettings()
{
TypeNameHandling =TypeNameHandling.Objects,
TypeNameAssemblyFormat = System.Runtime.Serialization.Formatters.FormatterAssemblyStyle.Simple
});
Run Code Online (Sandbox Code Playgroud)
对于反序列化,请使用以下代码:
JsonConvert.DeserializeObject(Encoding.UTF8.GetString(bData),type,
new JsonSerializerSettings(){TypeNameHandling = TypeNameHandling.Objects}
);
Run Code Online (Sandbox Code Playgroud)
只需记下JsonSerializerSettings对象初始化程序,这对您很重要.
ada*_*sty 11
我通过使用名为TypeNameHandling.All的JsonSerializerSettings的特殊设置解决了这个问题
TypeNameHandling设置包括序列化JSON和读取类型信息时的类型信息,以便在反序列化JSON时创建创建类型
连载:
var settings = new JsonSerializerSettings { TypeNameHandling = TypeNameHandling.All };
var text = JsonConvert.SerializeObject(configuration, settings);
Run Code Online (Sandbox Code Playgroud)
反序列化:
var settings = new JsonSerializerSettings { TypeNameHandling = TypeNameHandling.All };
var configuration = JsonConvert.DeserializeObject<YourClass>(json, settings);
Run Code Online (Sandbox Code Playgroud)
类YourClass可能有任何类型的基类型字段,它将被正确序列化.
在我的项目中,这段代码始终充当默认序列化程序,它序列化指定的值,就好像没有特殊的转换器一样:
serializer.Serialize(writer, value);
Run Code Online (Sandbox Code Playgroud)
| 归档时间: |
|
| 查看次数: |
222634 次 |
| 最近记录: |