JsonJack:无法将java.util.LinkedHashMap强制转换为X
1. 概述
Jackson是一个广泛使用的Java库,它使可以方便地对JSON或XML进行序列化/反序列化。
有时,当尝试将JSON或XML反序列化为对象集合时,可能会遇到“ java.lang.ClassCastException:java.util.LinkedHashMap无法转换为X”。
2.问题分析
简单的来说,JSON反序列化时,未提供目标信息,它将使用目标类型:LinkedHashMap。接下来,我们来模拟这样的场景。
2.1 数据准备
首先先创建已经基础类:Person。
1 public class Person { 2 private String name; // 名称 3 private int age; // 年龄 4 // …… 这里省略了getter,setter等方法。 5 }
创建一个用于测试的API接口,http://localhost:8090/tsy/cip/test/getPersion 。返回的JSON数据如下:
1 [ 2 { 3 "name": "张三", 4 "age": 22 5 }, 6 { 7 "name": "李四", 8 "age": 22 9 } 10 ]
我们创建测试数据,调用接口。
1 @Test 2 public void testError(){ 3 RestTemplate restTemplate = new RestTemplate(); 4 // 提交表单 5 HttpHeaders headers = new HttpHeaders(); 6 headers.setContentType(MediaType.APPLICATION_JSON); 7 headers.add("Content-Type","application/json;charset=UTF-8"); 8 //将请求头部和参数合成一个请求 9 List<Person> result = restTemplate.getForObject("http://localhost:8090/tsy/cip/test/getPersion" , ArrayList.class); 10 System.out.println("result=>" + result); 11 System.out.println("[0]Name=>" + result.get(0).getName()); // 报错java.lang.ClassCastException: java.util.LinkedHashMap cannot be cast to com.tsyapp.crm.domain.Person 12 }
运行结果如下:
2.2 错误分析
已经声明了类型为List<Person>,但是为什么Jackson尝试将LinkedHashMap类型转换为Book类呢?此外,LinkedHashMap来自何处?
-
restTemplate.getForObject,传递的对象是ArrayList.class 。所以JSON可以将他们反序列化为数组,但它并不知道数组内的对象是什么类型。
- 当未提供目标信息时,它使用默认类型LinkedHashMap。