为何Gson序列化时null值未被序列化,对应键值对缺失?
解决Gson序列化时null字段缺失的问题
这个问题很常见——Gson的默认行为就是忽略值为null的字段,所以当你的end字段为null时,它不会出现在生成的JSON里。下面给你两种实用的解决方法:
方法1:全局配置Gson实例序列化null值
这是最简便的方案,创建Gson实例时通过GsonBuilder开启serializeNulls()选项,这样所有null值的字段都会被序列化为"key": null的形式:
// 创建支持序列化null的Gson实例 Gson gson = new GsonBuilder() .serializeNulls() .create(); // 序列化你的History对象 History history = new History("area123", "user456", 1620000000L, null); String json = gson.toJson(history);
生成的JSON会包含end字段:
{ "areaId": "area123", "userId": "user456", "start": 1620000000, "end": null }
方法2:针对单个字段配置(适合特殊需求)
如果你不想全局开启null序列化,只想让end字段在null时显示,可以自定义TypeAdapter单独处理History类。这个方案相对繁琐,适合有特定序列化规则的场景:
class HistoryTypeAdapter extends TypeAdapter<History> { private final Gson gson = new Gson(); @Override public void write(JsonWriter out, History history) throws IOException { out.beginObject(); out.name("areaId").value(history.areaId); out.name("userId").value(history.userId); out.name("start").value(history.start); // 强制写入end字段,即使值为null out.name("end"); if (history.end == null) { out.nullValue(); } else { out.value(history.end); } out.endObject(); } @Override public History read(JsonReader in) throws IOException { // 实现反序列化逻辑 JsonObject jsonObject = gson.fromJson(in, JsonObject.class); String areaId = jsonObject.get("areaId").getAsString(); String userId = jsonObject.get("userId").getAsString(); long start = jsonObject.get("start").getAsLong(); Long end = jsonObject.has("end") && !jsonObject.get("end").isJsonNull() ? jsonObject.get("end").getAsLong() : null; return new History(areaId, userId, start, end); } }
使用这个自定义TypeAdapter:
Gson gson = new GsonBuilder() .registerTypeAdapter(History.class, new HistoryTypeAdapter()) .create();
补充说明
你POJO里的@NonNull和@Nullable是JetBrains的注解(比如IntelliJ IDEA的静态检查注解),Gson本身不会识别这些注解,它们只用于IDE代码提示,不影响序列化行为。
内容的提问来源于stack exchange,提问作者Dan Anderson
相关产品推荐
相关产品推荐

