Java基础之深复制,浅复制

版权声明:本文为博主原创文章,未经博主允许不得转载。 https://blog.csdn.net/swjtu2014112194/article/details/85112593

引用对象

Person a = new Person();
Person b = a;
这里的b是对象的引用,相当于C++中的指针。
b和a是同一个对象,指向内存中的同一段。
对b修改就相当于对a修改。

那么怎么可以对b修改而不影响a呢?答案是使用clone方法。

clone方法

Java中的所有类默认继承自Object类,而Object类中提供了一个clone()方法。这个方法的作用是返回一个Object对象的复制。clone方法返回的是一个新的对象而不是一个引用。
以下是使用clone()方法的步骤:

  1. 实现clone的类首先要继承Cloneable接口。Cloneable接口实质上是一个标识接口,没有任何接口方法。
  2. 在类中重写Object类中的clone()方法。
  3. 在clone()方法中调用super.clone()。无论当前类的继承结构是什么,super.clone()都会直接或间接调用Object类的clone()方法。
  4. 把浅复制的引用指向原型对象新的克隆体。
    例子:
public class test1 {

	public static void main(String[] args) {
		Person a = new Person();
		a.setName("小红");
		Person b = (Person) a.clone();
		b.setName("小明");
		System.out.println("a:"+ a.getName());
		System.out.println("b:"+ b.getName());
	}
}



class Person implements Cloneable{
	
	private String name;
	
	public void setName(String name) {
		this.name = name;
	}
	
	public String getName() {
		return name;
	}
	
	public Object clone() {
		Object o = null;
		try {
			o = (Person)super.clone();
		}catch (CloneNotSupportedException e) {
			e.printStackTrace();
		}
		return o;
	}
}

当类中只有一些基本的数据类型时,采用上述方法就可以了,但是当类中包含了一些对象时,就需要用到深复制了,实现方法是在对对象调用clone()方法完成复制后,接着对对象中的非基本类型的属性也调用clone()方法完成深复制。
示例如下:

import java.text.ParseException;
import java.text.SimpleDateFormat;
import java.util.Date;

public class test1 {

	public static void main(String[] args) throws ParseException {
		Person a = new Person();
		Person b = (Person)a.clone();
		
		SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd");
		Date date = sdf.parse("2018-10-17");
		a.setBirth(date);
		date = sdf.parse("2018-11-27");
		b.setBirth(date);
		
		System.out.println("a:" + a.getBirth());
		System.out.println("b:" + b.getBirth());
	}
}
class Person implements Cloneable{
	
	private Date birth = new Date();
	
	public void setBirth(Date birth) {
		this.birth = birth;
	}
	
	public Date getBirth() {
		return birth;
	}
	
	public Object clone() {
		Person o = null;
		try {
			o = (Person)super.clone();
		}catch (CloneNotSupportedException e) {
			e.printStackTrace();
		}
		//实现深复制
		o.birth = (Date) this.getBirth().clone();
		return o;
	}
}

clone()方法具有保护机制。Object中的clone()被声明为protected。以Person类为例,通过声明为protected,就可以保证只有Person类里面才能“克隆”Person对象。

浅复制与深复制

浅复制:被复制对象的所有变量都含有与原来对象相同的值,而所有对其他对象的引用仍然指向原来的对象。换言之,浅复制仅仅复制所考虑的对象,而不复制它所引用的对象。

深复制:被复制对象的所有变量都含有与原来对象相同的值,除了那些引用其他变量的变量。
引用其他对象的变量将指向被复制的新对象(新内存空间)。换言之,深复制把复制的对象所引用的对象都复制了一遍。
在这里插入图片描述

猜你喜欢

转载自blog.csdn.net/swjtu2014112194/article/details/85112593