注意
spring 的beanutil copyProperties() 、Apache Commons BeanUtils 都是浅拷贝
浅拷贝 和 深拷贝 的区别
- 浅拷贝只是拷贝了源对象的地址,所以源对象的值发生变化时,拷贝对象的值也会发生变化
- 深拷贝则是拷贝了源对象的所有值,所以即使源对象的值发生变化时,拷贝对象的值也不会改变。
深拷贝方案
1. Gson 对象
Gson gson = new Gson();
UserGson copyUser = gson.fromJson(gson.toJson(user), UserGson.class);
@Data
public class UserGson {
private String userName;
private AddressGson address;
public UserGson() {
}
public UserGson(String userName, AddressGson address) {
this.userName = userName;
this.address = address;
}
public static void main(String[] args) {
AddressGson address = new AddressGson("小区1", "小区2");
UserGson user = new UserGson("小李", address);
// 使用Gson序列化进行深拷贝
Gson gson = new Gson();
UserGson copyUser = gson.fromJson(gson.toJson(user), UserGson.class);
user.getAddress().setAddress1("小区3");
// false
System.out.println(user == copyUser);
// false
System.out.println(user.getAddress().getAddress1().equals(copyUser.getAddress().getAddress1()));
}
}
1. Gson List
List list= gson.fromJson(jsonList, new TypeToken<List>() {}.getType());
// 2.把jsonList转化为一个list对象
String jsonList="[{'userid':'1881140130','username':'三哥','usersex':'男','banji':'计算机1班','phone':'18255052351'},"
+ "{'userid':'1881140131','username':'蜂','usersex':'男','banji':'计算机1班','phone':'18355092351'},"
+ "{'userid':'1881140132','username':'宝','usersex':'男','banji':'计算机1班','phone':'18955072351'}]";
Gson gson=new Gson();
List<Person> list= gson.fromJson(jsonList, new TypeToken<List<Person>>() {}.getType());
for (Person person1 : list) {
System.out.println(person1.toString());
}
Jackson方式
ObjectMapper objectMapper = new ObjectMapper();
UserJackson copyUser = objectMapper.readValue(objectMapper.writeValueAsString(user), UserJackson.class);
@Data
public class AddressJackson {
private String address1;
private String address2;
public AddressJackson() {
}
public AddressJackson(String address1, String address2) {
this.address1 = address1;
this.address2 = address2;
}
}
@Data
public class UserJackson {
private String userName;
private AddressJackson address;
public UserJackson() {
}
public UserJackson(String userName, AddressJackson address) {
this.userName = userName;
this.address = address;
}
public static void main(String[] args) throws JsonProcessingException {
AddressJackson address = new AddressJackson("小区1", "小区2");
UserJackson user = new UserJackson("小李", address);
// 使用Jackson序列化进行深拷贝
ObjectMapper objectMapper = new ObjectMapper();
UserJackson copyUser = objectMapper.readValue(objectMapper.writeValueAsString(user), UserJackson.class);
user.getAddress().setAddress1("小区3");
// false
System.out.println(user == copyUser);
// false
System.out.println(user.getAddress().getAddress1().equals(copyUser.getAddress().getAddress1()));
}
}
list 方式
@Slf4j
public class JacksonApp {
public static void main(String[] args) throws JsonProcessingException {
String jsonString = "[{ \"productId\": \"1\", \"quantity\": 1 }]";
listJson2List(jsonString);
}
private static void listJson2List(String jsonString) {
// ObjectMapper对象
ObjectMapper objectMapper = new ObjectMapper();
// TypeReference<T>对象,因为是抽象类所以要追加{}实现
TypeReference<List<CartDTO>> listTypeReference = new TypeReference<List<CartDTO>>(){};
// 读取字符串,开始转换
try {
List<CartDTO> cartDTOList = objectMapper.readValue(jsonString, listTypeReference);
log.info("结果类型={}",cartDTOList.getClass());
log.info("结果List的长度={}",cartDTOList.size());
log.info("结果List的第一个元素={}",cartDTOList.get(0));
} catch (JsonProcessingException e) {
throw new RuntimeException(e);
}
}
}