C# Newtonsoft.JSON条件属性源
我正在使用Newtonsoft JSON进行序列化和反序列化。 我有json表示字段,其中title属性表示显示名称:C# Newtonsoft.JSON条件属性源,c#,.net,json,serialization,json.net,C#,.net,Json,Serialization,Json.net,我正在使用Newtonsoft JSON进行序列化和反序列化。 我有json表示字段,其中title属性表示显示名称: { "ID": { "type": "integer", "title": "ID Display Name" }, "TITLE": { "type": "string", "title": "Title Display name" }, "NAME": { "type": "string", "title"
{
"ID": {
"type": "integer",
"title": "ID Display Name"
},
"TITLE": {
"type": "string",
"title": "Title Display name"
},
"NAME": {
"type": "string",
"title": "Name"
},
"CUSTOM_123": {
"type": "string",
"title": "CUSTOM_123",
"formLabel": "CUSTOM_123 Display Name"
}
// ... etc
}
我有课:
public class Field
{
public string Title { get; set; }
public string Type { get; set; }
}
现在一切正常。但当字段名以“CUSTOM_”开头时,我需要从属性“formLabel”序列化“Title”
如何实现条件属性源?如果JSON中的属性名称以
自定义
字符串开头,您可以将JSON解析为,然后枚举所有属性,将它们逐个反序列化为字段
实例,并更新标题
值
var json=JObject.Parse(jsonString);
foreach(json.Properties()中的var属性)
{
var field=property.Value.ToObject();
if(property.Name.StartsWith(“自定义”)和&property.Value为JObject propertyObject)
{
field.Title=propertyObject[“formLabel”]?.Value();
}
}
这种方法比编写自定义转换器更简单,我相信您可以使用Newtonsoft和custom
JsonConverter对对象进行反序列化
您的JSON结构是一个JSON对象,它包含多个子JSON对象(字段)。因此,当将其反序列化到.NET时,您可以为父级创建一个单独的类,该类将有一个字段列表
。您还可以将JSON更改为数组而不是对象,并反序列化为列表
IList fields=JsonConvert.DeserializeObject(json,new CustomJsonConverter());
公共类CustomJsonConverter:JsonConverter
{
公共重写void WriteJson(JsonWriter编写器、对象值、JsonSerializer序列化器)
{
抛出新的NotImplementedException();
}
公共重写对象ReadJson(JsonReader阅读器,类型objectType,对象existingValue,JsonSerializer序列化程序)
{
IList字段=新列表();
JObject obj=JObject.Load(读卡器);
foreach(对象Children()中的JToken子对象)
{
字段=新字段();
JProperty fieldProp=(JProperty)子级;
JObject fieldValue=(JObject)fieldProp.Value;
字符串fieldName=fieldProp.Name;
if(fieldName.StartsWith(“自定义”)
{
field.Title=(字符串)fieldValue[“formLabel”];
field.Type=(字符串)fieldValue[“Type”];
}
其他的
{
field.Title=(字符串)fieldValue[“Title”];
field.Type=(字符串)fieldValue[“Type”];
}
字段。添加(字段);
}
返回字段;
}
公共覆盖布尔CanConvert(类型objectType)
{
返回true;
}
}
公共类字段
{
公共字符串标题{get;set;}
公共字符串类型{get;set;}
}
使用自定义JsonConverter就可以做到这一点,因此您将分离反序列化业务,并可以根据需要在Convert方法中包含更多业务。因此,在第一行中,牛顿软件通常将我们的对象序列化到字段中,然后为“custom_u2;”定制业务,工作小提琴
代码如下:
using Newtonsoft.Json;
using Newtonsoft.Json.Linq;
using System;
using System.Collections.Generic;
using System.Collections.Specialized;
using System.IO;
namespace testapp
{
class Program
{
static void Main(string[] args)
{
string json = @"
{
""ID"": {
""type"": ""integer"",
""title"": ""ID Display Name""
},
""TITLE"": {
""type"": ""string"",
""title"": ""Title Display name""
},
""NAME"": {
""type"": ""string"",
""title"": ""Name""
},
""CUSTOM_123"": {
""type"": ""string"",
""title"": ""CUSTOM_123"",
""formLabel"": ""CUSTOM_123 Display Name""
}
}";
List<Field> result = JsonConvert.DeserializeObject<List<Field>>(json, new JobInfoConverter());
}
public class Field
{
public string title { get; set; }
public string type { get; set; }
}
public class JobInfoConverter : JsonConverter
{
public override object ReadJson(JsonReader reader, Type objectType, object existingValue, JsonSerializer serializer)
{
try
{
List<Field> result = new List<Field>();
var content = JObject.Load(reader);
foreach (var prop in content.Properties())
{
var parsedValue = prop.Value.ToObject<Field>();
if (prop.Name.StartsWith("CUSTOM_"))
{
parsedValue.title = prop.Value["formLabel"].ToString();
}
result.Add(parsedValue);
}
return result;
}
catch (Exception ex)
{
return null;
}
}
public override void WriteJson(JsonWriter writer, object value, Newtonsoft.Json.JsonSerializer serializer) => throw new NotImplementedException();
public override bool CanConvert(Type objectType)
{
return true;
}
public override bool CanWrite => true;
}
}
使用Newtonsoft.Json;
使用Newtonsoft.Json.Linq;
使用制度;
使用System.Collections.Generic;
使用System.Collections.Specialized;
使用System.IO;
命名空间testapp
{
班级计划
{
静态void Main(字符串[]参数)
{
字符串json=@”
{
“ID”:{
“”类型“”:“”整数“”,
“”标题“”:“”ID显示名称“”
},
“标题”:{
“”类型“”:“”字符串“”,
“标题”:“标题显示名称”
},
“姓名”:{
“”类型“”:“”字符串“”,
“标题”:“名称”
},
“海关”123“:{
“”类型“”:“”字符串“”,
“标题”:“自定义名称”,
“formLabel”“:”“自定义显示名称”
}
}";
List result=JsonConvert.DeserializeObject(json,new JobInfoConverter());
}
公共类字段
{
公共字符串标题{get;set;}
公共字符串类型{get;set;}
}
公共类JobInfoConverter:JsonConverter
{
公共重写对象ReadJson(JsonReader阅读器,类型objectType,对象existingValue,JsonSerializer序列化程序)
{
尝试
{
列表结果=新列表();
var content=JObject.Load(读卡器);
foreach(content.Properties()中的var prop)
{
var parsedValue=prop.Value.ToObject();
if(prop.Name.StartsWith(“自定义”))
{
parsedValue.title=prop.Value[“formLabel”].ToString();
}
结果.Add(parsedValue);
}
返回结果;
}
捕获(例外情况除外)
{
返回null;
}
}
public override void WriteJson(JsonWriter writer,对象值,Newtonsoft.Json.JsonSerializer serializer)=>抛出新的NotImplementedException();
公共覆盖布尔CanConvert(类型objectType)
{
返回true;
}
public override bool CanWrite=>true;
}
}
}如果同时提供标题和fromLable,会发生什么情况?@Gleb它是否回答了您的问题,您需要更多详细信息或信息?