RestTemplate 获取对象列表 - 为什么使用 ParameterizedTypeReference 而不是对象数组?

RestTemplate get list of objects - Why use ParameterizedTypeReference instead of object array?

我正在尝试使用 Spring RestTemplate 获取对象列表。我很困惑为什么选择 ParameterizedTypeReference 方法来使用 restTemplate 而不是仅使用 Object[].class?

来获取对象列表

我检查了多个建议使用 ParameterizedTypeReference 的答案。但为什么我不能只使用 Object[].class?我有什么限制?

我已经检查了这个 link () 它说,我只能将 Object[] 用于简单的情况,并且在处理复杂的 json 结构时必须获取 ParameterizedTypeReference .有人可以解释一下在什么情况下我不能使用 Object[] 方法吗?

参数化类型引用方式:

ResponseEntity<List<Rating>> responseEntity =
                restTemplate.exchange("http://localhost:8084/ratingsdata/user/" + userId,
                        HttpMethod.GET, null, new ParameterizedTypeReference<List<Rating>>() {
                        });
List<Rating> ratings = responseEntity.getBody();

对象[]方法:

List<Rating> ratings = Arrays.asList(restTemplate.getForObject("http://localhost:8084/ratingsdata/user/"+userId, Rating[].class));

答案很简单,在运行时保留类型信息。

列表可以充当数组,但数组不能充当列表。为什么你正在做的事情是有效的,因为你正在将一个数组转换为一个列表,并且如上所述,一个列表可以充当一个数组,所以你这次是安全的。

但总的来说,铸造是一种不好的做法。

当你投射一些东西时,你是在冒险,你基本上是在强迫编译器"trust you"做你正在做的事情。因此,不是编译器告诉你什么是对的或错的,而是你告诉编译器什么是对的和错的,这是一种风险,破坏东西的风险。很难,因为 如果你在运行时出错,我们可能会崩溃。难以控制。

有很多程序员有很多意见,但只有一个编译器,一个意见,我们应该相信它。

回到问题,ParameterizedTypeReference<T>.class到底是做什么的?

如果您查看它的构造函数,您会发现它就像一个类型信息的容器。通过执行 new ParameterizedTypeReference<List<Foo.class>> {};,您在传入类型时实例化了一个匿名的 class。然后在构造函数中,它从传递的类型中提取类型信息并将其存储在内部。然后稍后我们可以做 getType() 来获取类型信息,这样我们就可以在运行时做一个类型安全的 "casting"。

    final ParameterizedTypeReference<List<String>> typeRef = new ParameterizedTypeReference<>() {};
    final Type type = typeRef.getType();
    final String typeName = type.getTypeName();
    System.out.println(typeName);
    // will print "java.util.List<java.lang.String>"

此模式称为 "Super type tokens",您可以在此处阅读更多相关信息 Neal Gafter's blog - Super Type Tokens