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

如何用Gson/Retrofit将带点分隔注解的Java POJO序列化为嵌套JSON

解决方案:基于Gson自定义序列化器实现嵌套JSON生成

你可以通过实现自定义Gson JsonSerializer,结合你已有的convertToObj函数,实现将带点分隔@SerializedName的Java类序列化为嵌套JSON的需求。以下是完整实现步骤:

1. 实现自定义序列化器

这个序列化器会遍历类的所有字段,读取@SerializedName标注的键和字段值,将点分隔键转换为嵌套Map并合并,最终生成目标JSON。

import com.google.gson.*;
import java.lang.reflect.Field;
import java.util.HashMap;
import java.util.Map;

public class InputDataSerializer implements JsonSerializer<InputData> {
    @Override
    public JsonElement serialize(InputData src, java.lang.reflect.Type typeOfSrc, JsonSerializationContext context) {
        Map<String, Object> rootMap = new HashMap<>();

        for (Field field : src.getClass().getDeclaredFields()) {
            try {
                field.setAccessible(true);
                Object fieldValue = field.get(src);
                if (fieldValue == null) continue;

                // 获取序列化键:优先用@SerializedName,否则用字段名
                SerializedName serializedName = field.getAnnotation(SerializedName.class);
                String targetKey = serializedName != null ? serializedName.value() : field.getName();

                // 生成当前字段的嵌套Map
                Map<String, Object> fieldNestedMap = convertToObj(targetKey, fieldValue.toString());
                // 合并到根Map(处理同前缀的嵌套结构)
                mergeNestedMaps(rootMap, fieldNestedMap);
            } catch (IllegalAccessException e) {
                e.printStackTrace();
            }
        }

        return context.serialize(rootMap);
    }

    // 合并两个嵌套Map,处理层级结构
    private void mergeNestedMaps(Map<String, Object> destMap, Map<String, Object> srcMap) {
        for (Map.Entry<String, Object> entry : srcMap.entrySet()) {
            String key = entry.getKey();
            Object srcValue = entry.getValue();
            Object destValue = destMap.get(key);

            if (destValue instanceof Map && srcValue instanceof Map) {
                // 递归合并子Map
                mergeNestedMaps((Map<String, Object>) destValue, (Map<String, Object>) srcValue);
            } else {
                destMap.put(key, srcValue);
            }
        }
    }

    // 你已有的键转嵌套Map函数
    private static HashMap<String, Object> convertToObj(String key, String value) {
        HashMap<String, Object> root = new HashMap<>();
        Map<String, Object> currentMap = root;
        String[] keyParts = key.split("\\.");
        for (int i = 0; i < keyParts.length; i++) {
            String part = keyParts[i];
            if (i == keyParts.length - 1) {
                currentMap.put(part, value);
            } else {
                Map<String, Object> subMap = (Map<String, Object>) currentMap.get(part);
                if (subMap == null) {
                    subMap = new HashMap<>();
                    currentMap.put(part, subMap);
                }
                currentMap = subMap;
            }
        }
        return root;
    }
}

2. 使用Gson序列化InputData

创建Gson实例时注册自定义序列化器,即可生成期望的嵌套JSON:

public class SerializationDemo {
    public static void main(String[] args) {
        InputData input = new InputData();

        Gson gson = new GsonBuilder()
                .registerTypeAdapter(InputData.class, new InputDataSerializer())
                .setPrettyPrinting() // 可选:格式化输出JSON
                .create();

        String nestedJson = gson.toJson(input);
        System.out.println(nestedJson);
    }
}

3. 适配Retrofit

如果需要在Retrofit中使用,只需将上述Gson实例传入GsonConverterFactory:

Retrofit retrofit = new Retrofit.Builder()
        .baseUrl("your_api_base_url")
        .addConverterFactory(GsonConverterFactory.create(gson))
        .build();

效果验证

运行上述代码后,会输出你期望的嵌套JSON结构:

{
    "type": "Usage",
    "timeframe": "custom",
    "timePeriod": {
        "from": "2022-07-14T00:00:00+00:00",
        "to": "2022-07-26T23:59:59+00:00"
    }
}

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.25 04:27:27