1、什么叫Java浅拷贝?
浅拷贝是按位拷贝对象,它会创建一个新对象,这个对象有着原始对象属性值的一份精确拷贝。如果属性是基本类型,拷贝的就是基本类型的值;如果属性是内存地址(引用类型),拷贝的就是内存地址 ,因此如果其中一个对象改变了这个地址,就会影响到另一个对象。
2、什么叫Java深拷贝?
深拷贝复制变量值,对于引用数据,则递归至基本类型后,再复制。深拷贝后的对象与原来的对象是完全隔离的,互不影响,对一个对象的修改并不会影响另一个对象。深拷贝相比于浅拷贝速度较慢并且花销较大。
3、Java浅拷贝和深拷贝的区别是什么?
通俗来讲浅拷贝的复制其引用,当引用指向的值改变时也会跟着变化;而深拷贝则是与原来的对象完全隔离,互不影响。
深拷贝的实现方法主要有两种:
(1) 通过重写clone方法来实现深拷贝(实现Cloneable接口)
推荐】慎用 Object 的 clone 方法来拷贝对象。
说明: 对象的 clone 方法默认是浅拷贝,若想实现深拷贝需要重写 clone 方法实现属性对象的拷贝。
与通过重写clone方法实现浅拷贝的基本思路一样,只需要为对象图的每一层的每一个对象都实现Clonneable接口并重写clone方法,最后在最顶层的类的重写的clone方法中调用所有的clone方法即可实现深拷贝。简单的说就是“每一层的每个对象都进行浅拷贝=深拷贝。
(2)推荐: 通过对象序列化实现深拷贝(实现Serializable接口)
虽然层次调用clone方法可以实现深拷贝,但是显然代码量实在太大。特别对于属性数量比较多、层次比较深的类而言,每个类都要重写clone方法太过繁琐。
将对象序列化为字节序列后,默认会将该对象的整个对象图进行序列化,再通过反序列即可完美地实现深拷贝。
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.ObjectInputStream;
import java.io.ObjectOutputStream;
public class ObSriaInOut {
public static void main(String[] args) throws IOException, ClassNotFoundException{
Persen p=in();
Persen p2=out();
System.out.println(p);
System.out.println(p2);
}
public static Persen out() throws IOException, FileNotFoundException {
//創建對象輸出流,在使用對象輸出流時候必須進行對象序列化,否知會報錯java.io.NotSerializableException
ObjectOutputStream oos=new ObjectOutputStream(new FileOutputStream("f:\\person.bin",false));
//創建一個persn對象
Persen p = new Persen("張大",22,5000);
//寫出對象流
oos.writeObject(p);
//關閉流
oos.flush();
oos.close();
return p;
}
public static Persen in() throws IOException, FileNotFoundException, ClassNotFoundException {
//創建對象輸入流
ObjectInputStream ois=new ObjectInputStream(new FileInputStream("f:\\person.bin"));
//讀取對象流
Persen p=(Persen) ois.readObject();
ois.close();
System.out.println(p.toString());
return p;
}
}
//persen类
package com.javabase.obj.serializable;
import java.io.Serializable;
public class Persen implements Serializable{
private String name;
private double sal;
private int age;
public Persen() {
super();
}
//構造方法用於初始化成員參數
public Persen(String name, double sal, int age) {
super();
this.name = name;
this.sal = sal;
this.age = age;
}
@Override
public String toString() {
return this.name+"---"+this.age+"---"+this.sal;
}
}
相关文章
暂无评论...