C#使用Newtonsoft.Json将平级x、y属性嵌套为position对象的方案求解
C# 使用Newtonsoft.Json实现平级x/y字段转嵌套position结构解决方案
问题核心
需要将源JSON中平级的x、y属性,转换为目标JSON中嵌套在position下的结构,同时完成其他字段的映射替换。
方案1:手动对象映射(最推荐,可控性最高)
步骤1:修正实体类定义
首先分别定义源JSON反序列化用类和目标JSON序列化用类,不要混用,避免属性冲突:
// 源JSON反序列化专用类 public class SourceRoot { public List<SourceItem> n { get; set; } } public class SourceItem { public string type { get; set; } public string id { get; set; } public int x { get; set; } public int y { get; set; } public string text { get; set; } public string fill { get; set; } public string physicalLocation { get; set; } public int[] thisInterfaceTypes { get; set; } public int[] otherInterfaceTypes { get; set; } public string[] link { get; set; } public object[] otherLocationEntityIds { get; set; } public bool[] shouldUseLegacyLinkTypes { get; set; } } // 目标JSON序列化专用类 public class TargetRoot { public List<Cell> cells { get; set; } } public class Cell { public string type { get; set; } public Size size { get; set; } public Position position { get; set; } public int angle { get; set; } public string id { get; set; } public int z { get; set; } public Attrs attrs { get; set; } // 其他需要的属性自行补充 } public class Size { public int width { get; set; } public int height { get; set; } } public class Position { public int x { get; set; } public int y { get; set; } } // Attrs相关的嵌套类你已经有对应结构的话直接用,没有就按目标JSON定义即可
步骤2:编写映射转换逻辑
// 1. 反序列化源JSON var sourceJson = "你的源JSON字符串"; var sourceData = JsonConvert.DeserializeObject<SourceRoot>(sourceJson); // 2. 手动映射到目标结构 var targetData = new TargetRoot { cells = sourceData.n.Select(item => new Cell { type = "app.Router", // 按你的规则替换type值 id = item.id, // 直接复用源ID,需要生成新的话自行替换 position = new Position { x = item.x, // 直接取源平级x赋值到嵌套position的x y = item.y // 直接取源平级y赋值到嵌套position的y }, size = new Size { width = 90, height = 35 }, // 固定值或者按规则计算 angle = 0, z = 1, attrs = new Attrs { // 你的attrs属性赋值逻辑,比如fill可以取源item.fill的值 } // 其他属性按你的规则赋值 }).ToList() }; // 3. 序列化得到目标JSON var targetJson = JsonConvert.SerializeObject(targetData, Formatting.Indented);
原有代码问题说明
你当前的类中存在多个标注[JsonExtensionData]的属性,Newtonsoft.Json规定一个类只能有一个被该特性标记的属性,多个会导致序列化/反序列化异常,这也是你之前x/y值为null的常见原因之一。
方案2:自定义JsonConverter(适合不想写映射逻辑的场景)
如果需要直接在序列化的时候自动转换,可以自定义转换器:
public class PositionConverter : JsonConverter { public override void WriteJson(JsonWriter writer, object value, JsonSerializer serializer) { var item = (N)value; writer.WriteStartObject(); // 写入其他正常属性 writer.WritePropertyName("type"); serializer.Serialize(writer, "app.Router"); writer.WritePropertyName("id"); serializer.Serialize(writer, item.entityId); // 写入嵌套position writer.WritePropertyName("position"); serializer.Serialize(writer, new { x = item.x, y = item.y }); // 其他属性按规则写入 writer.WriteEndObject(); } public override object ReadJson(JsonReader reader, Type objectType, object existingValue, JsonSerializer serializer) { throw new NotImplementedException(); } public override bool CanConvert(Type objectType) { return objectType == typeof(N); } }
使用的时候在序列化时传入转换器即可:
var json = JsonConvert.SerializeObject(yourObject, Formatting.Indented, new PositionConverter());
内容的提问来源于stack exchange,提问作者lpierpoint
相关产品推荐
相关产品推荐

