如何使用gson处理泛型类型?

irlmq6kh  于 2022-11-06  发布在  其他
关注(0)|答案(1)|浏览(206)

我创建了一个类来封装gson的序列化/反序列化行为。这个想法是让这个类完全通用,这样它就可以被需要它的软件的任何部分使用。

public class JsonParser {
    private static final Logger log = Logger.getLogger(JsonParser.class.getName());

    private static final Gson gson = new Gson();

    public static String convertToJson(Object object) {
        String result = gson.toJson(object);
        log.log(Level.INFO, "Result: {0}", result);
        return result;
    }

    public static <T extends Object> T convertToString(String jsonString, Class<T> object) {
        Type type = new TypeToken<T>() {}.getType();
        T result = gson.fromJson(jsonString, type);
        log.log(Level.INFO, "Result: {0}", result.toString());
        return result;
    }
}

我在反序列化(方法convertToString)中遇到了问题。测试结果= gson.fromJson(jsonString,类型为);会在编译阶段掷回这个错误:
“无法确定T的类型参数;不存在上限为T,java.lang.Object的类型变量T的唯一最大示例”
我知道这意味着代码在恢复时太模糊和不安全。在这个版本之前,我传递的是名为 object 的参数,而不是变量 type,但问题是返回的对象有问题,并在代码执行的后面抛出了NullPointerException。我阅读了有关Gson和泛型类型的问题,所以我进入了实际版本。
为了以防万一,下面是对有问题的方法的调用(响应是一个String):

JsonParser.convertToString(response, Response.class);

所以问题是:我如何使这个编译并在Intent中保持我的方法泛型?

p3rjfoxz

p3rjfoxz1#

不要在实用方法中创建类型标记:

Type type = new TypeToken<T>() {}.getType();

让呼叫者为您创建:

public static <T> T convertToString(String jsonString, TypeToken<T> typeToken) 
    T result = gson.fromJson(jsonString, typeToken.getType());
    log.log(Level.INFO, "Result: {0}", result.toString());
    return result;
}

示例:

class Pojo {
    private String field1;
    private int field2;

    @Override
    public String toString() {
        return "Pojo [field1=" + field1 + ", field2=" + field2 + "]";
    }
}

List<Pojo> list = convertToString("[{\"field1\":\"abc\", \"field2\" : 10}]", new TypeToken<List<Pojo>>() {});

assert list.size() == 1;
assert list.get(0).field1.equals("abc");
assert list.get(0).field2 == 10;

输出功率

INFO: Result: [Pojo [field1=abc, field2=10]]

附注:

  • 您的实用程序类名为JsonParser,它与同名的类from GSON lib冲突-这可能会造成不必要的混淆
  • 您将json字符串反序列化为对象的方法名为convertToString,但它的作用正好相反
  • 泛型类型参数<T extends Object>没有多大意义,java中的每个对象示例都扩展了Object,因此它可能只是<T>

相关问题