Java 深度克隆
来源:互联网 发布:淘宝买单机游戏 编辑:程序博客网 时间:2024/06/06 13:06
Java 深度克隆
工具类
import java.lang.reflect.Array;import java.lang.reflect.Constructor;import java.lang.reflect.Field;import java.lang.reflect.Method;import java.util.ArrayList;import java.util.Date;import java.util.List;import java.util.Map;public class BeanUtil{ /** * 基本数据类型的引用类型 */ private static List<Class<?>> baseType = new ArrayList<Class<?>>(); /* * 单一的数据类型 */ private static List<Class<?>> simpleType = new ArrayList<Class<?>>(); static { baseType.add(Byte.class); baseType.add(Short.class); baseType.add(Integer.class); baseType.add(Long.class); baseType.add(Float.class); baseType.add(Double.class); baseType.add(Character.class); baseType.add(Boolean.class); simpleType.addAll(baseType); simpleType.add(String.class); simpleType.add(Date.class); simpleType.add(java.sql.Date.class); } @SuppressWarnings("unchecked") public static <T> T deepClone(T pojo) throws Exception { if(pojo == null) return null; Class<?> pojoClass = pojo.getClass(); if(simpleType.contains(pojoClass) || pojoClass.getName().startsWith("[") || List.class.isAssignableFrom(pojoClass) || Map.class.isAssignableFrom(pojoClass)) { return (T) copyValue(pojoClass, pojo); } Constructor<T> constructor = (Constructor<T>) pojoClass.getDeclaredConstructor(); T bean = constructor.newInstance(); Field[] fields = pojo.getClass().getDeclaredFields(); for(Field field : fields) { copyFieldValue(pojo, bean, field); } return bean; } @SuppressWarnings("unchecked") public static <T> T copyValue(Class<T> clazz, Object oldPojo) throws Exception { if(oldPojo == null) return null; if(clazz.isPrimitive()) {//基本数据类型 return (T) oldPojo; } if(baseType.contains(clazz)) {//基本数据类型的引用类型 Method method = clazz.getMethod("valueOf", (Class<?>) clazz.getField("TYPE").get(null)); return (T) method.invoke(null, oldPojo); } if(clazz == String.class) { return (T) new String((String) oldPojo); } if(clazz == Date.class) { Date date = (Date) oldPojo; return (T) new Date(date.getTime()); } if(clazz == java.sql.Date.class) { java.sql.Date date = (java.sql.Date) oldPojo; return (T) new java.sql.Date(date.getTime()); } String clazzName = clazz.getName(); if(clazzName.startsWith("[")) {//数组 Object oldArray = oldPojo; int oldLen = Array.getLength(oldArray); Object firstObj = Array.get(oldArray, 0); Class<?> itemClazz = firstObj.getClass(); if(baseType.contains(itemClazz)) {//针对基础类型自动装箱成增强类型 if(clazzName.charAt(1) != '[' && clazzName.charAt(1) != 'L') { itemClazz = (Class<?>) itemClazz.getField("TYPE").get(null); } } Object newArray = Array.newInstance(itemClazz, oldLen); for(int i = 0; i < oldLen; i++) { Object item = Array.get(oldArray, i); Array.set(newArray, i, BeanUtil.deepClone(item)); } return (T) newArray; } if(List.class.isAssignableFrom(clazz)) {//List集合 List<?> oldList = (List<?>) oldPojo; List<Object> newList = oldList.getClass().getDeclaredConstructor(Integer.TYPE).newInstance(oldList.size()); for(Object obj : oldList) { newList.add(BeanUtil.deepClone(obj)); } return (T) newList; } if(Map.class.isAssignableFrom(clazz)) { Map<?, ?> oldMap = (Map<?, ?>) oldPojo; Map<Object, Object> newMap = oldMap.getClass().getDeclaredConstructor(Integer.TYPE).newInstance(oldMap.size()); for(Object key : oldMap.keySet()) { Object value = oldMap.get(key); newMap.put(BeanUtil.deepClone(key), BeanUtil.deepClone(value)); } return (T) newMap; } return BeanUtil.deepClone((T) oldPojo); } public static <T> void copyFieldValue(T oldPojo, T newPojo, Field field) throws Exception { if("serialVersionUID".equals(field.getName())) { return; } Class<?> clazz = field.getType(); //强制对此字段进行赋值操作 //http://blog.csdn.net/yaerfeng/article/details/7103397 field.setAccessible(true); if(clazz.isPrimitive()) {//基本数据类型 field.set(newPojo, field.get(oldPojo)); return; } Object oldValue = field.get(oldPojo); if(oldValue == null) { return; } field.set(newPojo, copyValue(clazz, oldValue)); }}
测试Pojo
BasePojo
public class BasePojo{ private String id; //getter、setter省略}
TestClass
import java.util.Arrays;import java.util.Date;import java.util.List;import java.util.Map;public class TestClass{ private String name; private int age; private boolean flag; private Double money; private Date borthDay; private BasePojo basePojo; private int[] intArr; private Double[] doubleArr; private List<BasePojo> basePojos; private Map<String, BasePojo> basePojoMap; //getter、setter省略}
测试类
import java.util.ArrayList;import java.util.HashMap;import java.util.List;import java.util.Map;import org.junit.Test;public class BeanUtilTest{ @Test public void test() throws Exception { int[] intArr = { 1, 2 }; Double[] doubleArr = new Double[] { 5.5, 6.6 }; BasePojo basePojo1 = new BasePojo(); BasePojo basePojo2 = new BasePojo(); BasePojo basePojo3 = new BasePojo(); BasePojo basePojo4 = new BasePojo(); BasePojo basePojo5 = new BasePojo(); basePojo1.setId("1"); basePojo2.setId("2"); basePojo3.setId("3"); basePojo4.setId("4"); basePojo5.setId("5"); List<BasePojo> basePojos = new ArrayList<BasePojo>(); basePojos.add(basePojo2); basePojos.add(basePojo3); Map<String, BasePojo> basePojoMap = new HashMap<String, BasePojo>(); basePojoMap.put(basePojo4.getId(), basePojo4); basePojoMap.put(basePojo5.getId(), basePojo5); TestClass tc1 = new TestClass(); System.out.println(tc1); tc1.setAge(24); tc1.setMoney(5.5); tc1.setName("xych"); tc1.setFlag(true); tc1.setIntArr(intArr); tc1.setDoubleArr(doubleArr); tc1.setBasePojo(basePojo1); tc1.setBasePojos(basePojos); tc1.setBasePojoMap(basePojoMap); System.out.println(tc1); TestClass tc2 = BeanUtil.deepClone(tc1); System.out.println(tc1); System.out.println(tc2); } @Test public void test1() throws Exception { int b = BeanUtil.deepClone(5); System.out.println(b); Character aa = 'y'; Character bb = BeanUtil.deepClone(aa); System.out.println(aa + " " + bb + " " + (aa == bb)); Integer aaa = 129; Integer bbb = BeanUtil.deepClone(aaa); System.out.println(aaa + " " + bbb + " " + (aaa == bbb)); } @Test public void test2() throws Exception { int[] arr = new int[] { 1, 2 }; int[] arr2 = BeanUtil.deepClone(arr); System.out.println(arr); System.out.println(arr2); arr2[1] = 3; System.out.println(arr[1]); System.out.println(arr2[1]); // String[] strArr1 = new String[] { "1", "2" }; String[] strArr2 = BeanUtil.deepClone(strArr1); strArr2[1] = "3"; System.out.println(strArr1 + " " + strArr1[1]); System.out.println(strArr2 + " " + strArr2[1]); System.out.println(strArr1[0] == strArr2[0]); // BasePojo[] bpArr1 = new BasePojo[2]; BasePojo bp1 = new BasePojo(); bp1.setId("1"); BasePojo bp2 = new BasePojo(); bp2.setId("2"); bpArr1[0] = bp1; bpArr1[1] = bp2; BasePojo[] bpArr2 = BeanUtil.deepClone(bpArr1); bpArr2[1].setId("5"); System.out.println(bpArr1[1].getId()); System.out.println(bpArr2[1].getId()); } @Test public void test3() throws Exception { List<String> strList1 = new ArrayList<String>(); strList1.add("1"); strList1.add("2"); List<String> strList2 = BeanUtil.deepClone(strList1); System.out.println(strList1); System.out.println(strList2); System.out.println(strList1.get(1) == strList2.get(1)); // List<BasePojo> bpList1 = new ArrayList<BasePojo>(); BasePojo bp1 = new BasePojo(); bp1.setId("1"); BasePojo bp2 = new BasePojo(); bp2.setId("2"); bpList1.add(bp1); bpList1.add(bp2); List<BasePojo> bpList2 = BeanUtil.deepClone(bpList1); System.out.println(bpList1); System.out.println(bpList2); } @Test public void test4() throws Exception { Map<String, String> map = new HashMap<String, String>(); map.put("1", "2"); map.put("3", "4"); Map<String, String> map2 = BeanUtil.deepClone(map); map2.put("3", "6"); System.out.println(map); System.out.println(map2); } public static void main(String[] args) throws Exception { new BeanUtilTest().test(); }}
测试结果
test()测试结果
test1()测试结果
5y y true129 129 false
test2()测试结果
[I@3cb89838[I@7b11a3ac23[Ljava.lang.String;@4310b053 2[Ljava.lang.String;@7ca83b8a 3false25
test3()测试结果
test4()测试结果
{3=4, 1=2}{3=6, 1=2}
源代码:https://github.com/Lanboo/com.xych
见 com.xych.framework.api.common.util
阅读全文
1 0
- java深度克隆
- java 深度克隆
- java的深度克隆
- java深度克隆方法
- java深度克隆
- Java对象深度克隆
- JAVA深度克隆
- java 深度克隆
- java List深度克隆
- java的深度克隆
- Java 深度克隆
- Java clone() 浅克隆与深度克隆
- Java clone() 影子克隆与深度克隆
- Java clone() 浅克隆与深度克隆
- Java clone() 浅克隆与深度克隆
- Java clone() 浅克隆与深度克隆
- Java clone() 浅克隆与深度克隆
- Java clone() 浅克隆与深度克隆
- Sql Server的登陆方式
- 基数排序(Radix Sort)
- 如何本地ssh远程登录阿里云服务器 ECS
- 一起写atom插件(2)——插件间的数据交互
- HttpServlet详解
- Java 深度克隆
- 关于MySQL返回插入的自增主键的几种方法
- OPCDAAuto.dll的C#使用方法浅析
- java如何对ArrayList中对象按照该对象某属性排序
- Android gradle issue: WARNING [Project: :app] shrinkResources does not yet work with useJack=true
- 谈一谈学习AngularJS2的一些package的心得
- Swift
- Java并发编程之ConcurrentHashMap(转)
- mysql hibernate java deecimal数据映射问题