You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

使用Newtonsoft.Json将JSON属性反序列化为子对象遇空值问题求助

解决JSON反序列化时Position属性为null的问题

这个问题的核心原因很明确:你的JSON结构里posx和posy是与pre同级的字段,但修改后的Vehicle类把这两个字段放到了嵌套的Position对象中。默认的Json.NET(Newtonsoft.Json)序列化器不会自动将平级的JSON属性映射到嵌套类的属性里,所以才会出现Position为null的情况。

下面提供两种实用的解决方法,都能让你复用Position类并正常完成反序列化:

方法一:自定义JsonConverter处理Vehicle类

创建一个专门的转换器,手动控制Vehicle对象的序列化和反序列化逻辑,把平级的posx和posy字段赋值给Position属性:

public class VehicleConverter : JsonConverter<Vehicle>
{
    public override Vehicle ReadJson(JsonReader reader, Type objectType, Vehicle existingValue, bool hasExistingValue, JsonSerializer serializer)
    {
        // 先把JSON读取为JObject,方便提取字段
        var jObject = JObject.Load(reader);
        
        var vehicle = new Vehicle
        {
            Prefix = jObject["pre"]?.ToString(),
            Position = new Position
            {
                Y = jObject["posx"]?.ToString(),
                X = jObject["posy"]?.ToString()
            }
        };
        
        // 如果需要处理其他字段(比如JSON里的"a"),可以在这里添加逻辑
        return vehicle;
    }

    public override void WriteJson(JsonWriter writer, Vehicle value, JsonSerializer serializer)
    {
        // 如果需要序列化Vehicle对象回JSON,也可以在这里定义逻辑
        var jObject = new JObject();
        jObject["pre"] = value.Prefix;
        if (value.Position != null)
        {
            jObject["posx"] = value.Position.Y;
            jObject["posy"] = value.Position.X;
        }
        jObject.WriteTo(writer);
    }
}

然后在Vehicle类上标记使用这个转换器:

[JsonConverter(typeof(VehicleConverter))]
public class Vehicle 
{ 
    [JsonProperty(PropertyName = "pre")] 
    public string Prefix { get; set; } 
    public Position Position { get; set; } 
}

这样反序列化时,转换器会自动把JSON里的posx和posy提取出来,创建Position对象并赋值给Vehicle的对应属性。

方法二:使用JsonConstructor构造函数

通过定义带参数的构造函数,并标记[JsonConstructor],让序列化器直接用JSON中的平级字段来初始化Position:

public class Vehicle 
{ 
    [JsonProperty(PropertyName = "pre")] 
    public string Prefix { get; set; } 
    public Position Position { get; set; } 

    // 标记这个构造函数为JSON反序列化时使用的构造器
    [JsonConstructor]
    public Vehicle(string pre, string posx, string posy)
    {
        Prefix = pre;
        Position = new Position
        {
            Y = posx,
            X = posy
        };
    }

    // 需要保留一个无参构造函数,供序列化器内部使用(如果需要序列化的话)
    public Vehicle() {}
}

这种方式更简洁,不需要额外写转换器,适合结构不复杂的场景。序列化器会自动匹配JSON中的字段名和构造函数的参数名(注意参数名要和JSON字段名一致,比如posx、posy),然后创建Position对象并赋值。

额外提示

如果JSON中还有其他不需要的字段(比如示例里的a),可以在Vehicle类中添加[JsonExtensionData]属性来忽略这些未知字段,避免反序列化出错:

[JsonExtensionData]
private IDictionary<string, JToken> _extraData;

这样就能完美解决你的问题,让Position属性正常被赋值啦!

内容的提问来源于stack exchange,提问作者Roberto

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.15 08:03:58