• java 深度拷贝 复制 深度复制


    1、深度拷贝、复制代码实现

    最近需要用到比较两个对象属性的变化,其中一个是oldObj,另外一个是newObj,oldObj是newObj的前一个状态,所以需要在newObj的某个状态时,复制一个一样的对象,由于JAVA不支持深层拷贝,因此专门写了一个方法。

    方法实现很简单,提供两种方式:

    一种是序列化成数据流,前提是所有对象(对象中包含的对象...)都需要继承Serializable接口,如果都继承了那很容易,如果没有继承,而且也不打算修改所有类,可以用第二种方式。

    第二种是将对象序列化为json,通过json来实现拷贝,这种方式需要用到net.sf.json.JSONObject。

    具体代码如下:

    import net.sf.json.JSONObject;
    
    import java.io.*;
    
    class deepCopy {
        /**
         * 深层拷贝
         *
         * @param <T>
         * @param obj
         * @return
         * @throws Exception
         */
        static <T> T copy(T obj) throws Exception {
            //是否实现了序列化接口,即使该类实现了,他拥有的对象未必也有...
            if(Serializable.class.isAssignableFrom(obj.getClass())){
                //如果子类没有继承该接口,这一步会报错
                try {
                    return copyImplSerializable(obj);
                } catch (Exception e) {
                    //这里不处理,会运行到下面的尝试json
                }
            }
            //如果序列化失败,尝试json序列化方式
            if(hasJson()){
                try {
                    return copyByJson(obj);
                } catch (Exception e) {
                    //这里不处理,下面返回null
                }
            }
            return null;
        }
    
        /**
         * 深层拷贝 - 需要类继承序列化接口
         * @param <T>
         * @param obj
         * @return
         * @throws Exception
         */
        @SuppressWarnings("unchecked")
        private static <T> T copyImplSerializable(T obj) throws Exception {
            ByteArrayOutputStream baos = null;
            ObjectOutputStream oos = null;
    
            ByteArrayInputStream bais = null;
            ObjectInputStream ois = null;
    
            Object o = null;
            //如果子类没有继承该接口,这一步会报错
            try {
                baos = new ByteArrayOutputStream();
                oos = new ObjectOutputStream(baos);
                oos.writeObject(obj);
                bais = new ByteArrayInputStream(baos.toByteArray());
                ois = new ObjectInputStream(bais);
    
                o = ois.readObject();
                return (T) o;
            } catch (Exception e) {
                throw new Exception("对象中包含没有继承序列化的对象");
            } finally{
                try {
                    assert baos != null;
                    baos.close();
                    assert oos != null;
                    oos.close();
                    assert bais != null;
                    bais.close();
                    assert ois != null;
                    ois.close();
                } catch (Exception e2) {
                    //这里报错不需要处理
                }
            }
        }
    
        /**
         * 是否可以使用json
         * @return
         */
        private static boolean hasJson(){
            try {
                Class.forName("net.sf.json.JSONObject");
                return true;
            } catch (Exception e) {
                return false;
            }
        }
    
        /**
         * 深层拷贝 - 需要net.sf.json.JSONObject
         * @param <T>
         * @param obj
         * @return
         * @throws Exception
         */
        @SuppressWarnings("unchecked")
        private static <T> T copyByJson(T obj) throws Exception {
            return (T) JSONObject.toBean(JSONObject.fromObject(obj),obj.getClass());
        }
    }
    

      

    只需要调用copy方法就行。

  • 相关阅读:
    js递归遍历
    .NET Core 图片操作在 Linux/Docker 下的坑
    远程桌面连接出现CredSSP的解决方法
    端口被占用解决方案
    当遇到“无法启动 IIS Express Web 服务器。”时的解决方案
    SQL Server索引设计
    python自动化之UI自动化框架搭建四--完成(关键字驱动)
    python自动化之UI自动化框架搭建三(关键字驱动)
    python自动化之UI自动化框架搭建二(关键字驱动)
    python自动化之ui自动化框架搭建一(关键字驱动)
  • 原文地址:https://www.cnblogs.com/wuzaipei/p/10528268.html
Copyright © 2020-2023  润新知