All Downloads are FREE. Search and download functionalities are using the official Maven repository.

com.i2soft.util.GsonMapDeserializerFix Maven / Gradle / Ivy

There is a newer version: 9.1.0.3
Show newest version
package com.i2soft.util;
/*
 *最近在研究网络请求数据解析的问题,发现json数据被强制转换为map结构的时候,会出现int变成double的问题
 *在stackoverflow上看到了一个这个How can I prevent gson from converting integers to doubles 的问题,采用了这个答案
 *https://stackoverflow.com/a/36529534/5279354答案
 */

import com.google.gson.*;
import com.google.gson.internal.LinkedTreeMap;

import java.lang.reflect.Type;
import java.util.ArrayList;
import java.util.List;
import java.util.Map;
import java.util.Set;

public class GsonMapDeserializerFix implements JsonDeserializer> {

    @Override
    public Map deserialize(JsonElement jsonElement, Type type, JsonDeserializationContext jsonDeserializationContext) throws JsonParseException {
        return (Map) read(jsonElement);
    }

    public Object read(JsonElement in) {
        if (in.isJsonArray()) {
            List list = new ArrayList<>();
            JsonArray arr = in.getAsJsonArray();
            for (JsonElement anArr : arr) {
                list.add(read(anArr));
            }
            return list;
        } else if (in.isJsonObject()) {
            Map map = new LinkedTreeMap();
            JsonObject obj = in.getAsJsonObject();
            Set> entitySet = obj.entrySet();
            for (Map.Entry entry : entitySet) {
                map.put(entry.getKey(), read(entry.getValue()));
            }
            return map;
        } else if (in.isJsonPrimitive()) {
            JsonPrimitive prim = in.getAsJsonPrimitive();
            if (prim.isBoolean()) {
                return prim.getAsBoolean();
            } else if (prim.isString()) {
                return prim.getAsString();
            } else if (prim.isNumber()) {
                Number num = prim.getAsNumber();
                // here you can handle double int/long values
                // and return any type you want
                // this solution will transform 3.0 float to long values
                if (Math.ceil(num.doubleValue()) == num.longValue())
                    return num.longValue();
                else {
                    return num.doubleValue();
                }
            }
        }
        return null;
    }
}