欧美bbbwbbbw肥妇,免费乱码人妻系列日韩,一级黄片

Java實(shí)現(xiàn)對象復(fù)制的方法實(shí)例

 更新時(shí)間:2023年08月02日 09:00:17   作者:ghostxiechuan  
這篇文章主要介紹了Java實(shí)現(xiàn)對象復(fù)制的方法實(shí)例,深復(fù)制:復(fù)制出來的對象中的變量(包括基本類型和字符串)和原來的對象的值都相同,引用對象也會(huì)指向復(fù)制出來的對象,需要的朋友可以參考下

一、概念

1.淺復(fù)制:復(fù)制出來的對象中的變量(包括基本類型和字符串)和原來的對象的值都相同,但是引用對象仍然指向原來的對象。

2.深復(fù)制:復(fù)制出來的對象中的變量(包括基本類型和字符串)和原來的對象的值都相同,引用對象也會(huì)指向復(fù)制出來的對象。

淺復(fù)制與深復(fù)制的不同之處就在于深復(fù)制還會(huì)復(fù)制對象的引用對象。

二、實(shí)現(xiàn)復(fù)制

1.使用Cloneable接口實(shí)現(xiàn)對象的復(fù)制

⑴淺復(fù)制

代碼如下

public class Food {
	private String name;
	public String getName() {
		return name;
	}
	public void setName(String name) {
		this.name = name;
	}
}
public class Animal implements Cloneable {
	// 動(dòng)物名
	private String name;
	// 食物
	private Food food;
	public String getName() {
		return name;
	}
	public void setName(String name) {
		this.name = name;
	}
	public Food getFood() {
		return food;
	}
	public void setFood(Food food) {
		this.food = food;
	}
	public Animal clone() {
		Animal animal = null;
		try {
			animal = (Animal) super.clone(); 
		} catch (CloneNotSupportedException e) {
			e.printStackTrace();
		}
		return animal;
	}
}
public class TestCopy {
	public static void main(String[] args) {
		Food food = new Food();
		food.setName("草");
		Animal animal = new Animal();
		animal.setName("羊");
		animal.setFood(food);
		Animal animal2 = animal.clone();
		System.out.println("animal動(dòng)物名:"+animal.getName());
		System.out.println("animal食物名:"+animal.getFood().getName());
		System.out.println("animal2動(dòng)物名:"+animal2.getName());
		System.out.println("animal2食物名:"+animal2.getFood().getName());
	}
}

打印結(jié)果是

animal動(dòng)物名:羊
animal食物名:草
animal2動(dòng)物名:羊
animal2食物名:草

此時(shí)已成功的實(shí)現(xiàn)了復(fù)制,但是這只是淺復(fù)制,引用對象Food并沒有被復(fù)制。

驗(yàn)證代碼

public class TestCopy {
	public static void main(String[] args) {
		Food food = new Food();
		food.setName("草");
		Animal animal = new Animal();
		animal.setName("羊");
		animal.setFood(food);
		Animal animal2 = animal.clone();
		System.out.println("animal動(dòng)物名:"+animal.getName());
		System.out.println("animal食物名:"+animal.getFood().getName());
		System.out.println("animal2動(dòng)物名:"+animal2.getName());
		System.out.println("animal2食物名:"+animal2.getFood().getName());
		//改變animal中food對象的值
		food.setName("樹葉");
		System.out.println("animal動(dòng)物名:"+animal.getName());
		System.out.println("animal食物名:"+animal.getFood().getName());
		System.out.println("animal2動(dòng)物名:"+animal2.getName());
		System.out.println("animal2食物名:"+animal2.getFood().getName());
	}
}

打印結(jié)果是

animal動(dòng)物名:羊
animal食物名:草
animal2動(dòng)物名:羊
animal2食物名:草
animal動(dòng)物名:羊
animal食物名:樹葉
animal2動(dòng)物名:羊
animal2食物名:樹葉

結(jié)果證明改變animal中的引用對象food,同時(shí)也改變了animal2中的引用對象food,說明animal和animal2的引用對象food是同一對象。

⑵深復(fù)制

要實(shí)現(xiàn)深復(fù)制,就必須同時(shí)復(fù)制引用對象,引用對象需實(shí)現(xiàn)Cloneable接口,F(xiàn)ood修改如下

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

Animal修改如下

public class Animal implements Cloneable {
	// 動(dòng)物名
	private String name;
	// 食物
	private Food food;
	public String getName() {
		return name;
	}
	public void setName(String name) {
		this.name = name;
	}
	public Food getFood() {
		return food;
	}
	public void setFood(Food food) {
		this.food = food;
	}
	public Animal clone() {
		Animal animal = null;
		try {
			animal = (Animal) super.clone(); 
		} catch (CloneNotSupportedException e) {
			e.printStackTrace();
		}
		//復(fù)制引用對象
		animal.food = food.clone();
		return animal;
	}
}

在clone方法中添加了引用對象的復(fù)制

使用上面的main方法測試,打印結(jié)果如下

animal動(dòng)物名:羊
animal食物名:草
animal2動(dòng)物名:羊
animal2食物名:草
animal動(dòng)物名:羊
animal食物名:樹葉
animal2動(dòng)物名:羊
animal2食物名:草

結(jié)果證明animal和animal2的引用對象food已經(jīng)不是同一對象了,此時(shí)成功地實(shí)現(xiàn)了深復(fù)制。

2.使用序列化(Serializable接口)實(shí)現(xiàn)對象的復(fù)制

使用Cloneable接口每個(gè)類都需要寫clone方法,工作量是很大的,我們可以使用序列化來實(shí)現(xiàn)對象的拷貝,這需要對象實(shí)現(xiàn)java.io.Serializable接口。

將上面的Animal和Food修改一下

import java.io.Serializable;
public class Food implements Serializable{
	private static final long serialVersionUID = 6466656398591229036L;
	private String name;
	public String getName() {
		return name;
	}
	public void setName(String name) {
		this.name = name;
	}
}
import java.io.Serializable;
public class Animal implements Serializable {
	private static final long serialVersionUID = -8424013303049171827L;
	// 動(dòng)物名
	private String name;
	// 食物
	private Food food;
	public String getName() {
		return name;
	}
	public void setName(String name) {
		this.name = name;
	}
	public Food getFood() {
		return food;
	}
	public void setFood(Food food) {
		this.food = food;
	}
}

再寫一個(gè)復(fù)制的工具類

import java.io.ByteArrayInputStream;
import java.io.ByteArrayOutputStream;
import java.io.ObjectInputStream;
import java.io.ObjectOutputStream;
import java.io.Serializable;
public class CopyUtil {
	@SuppressWarnings("unchecked")
	public static <T extends Serializable> T clone(T obj) {
		T cloneObj = null;
		ByteArrayOutputStream baos = null;
		ByteArrayInputStream bais = null;
		ObjectOutputStream oos = null;
		ObjectInputStream ois = null;
		try {
			// 序列化
			baos = new ByteArrayOutputStream();
			oos = new ObjectOutputStream(baos);
			oos.writeObject(obj);
			// 反序列化,生成新對象
			bais = new ByteArrayInputStream(
					baos.toByteArray());
			ois = new ObjectInputStream(bais);
			cloneObj = (T) ois.readObject();
		} catch (Exception e) {
			e.printStackTrace();
		} finally{
			try {
				if(oos!=null){
					oos.close();
				}
				if(baos!=null){
					baos.close();
				}
				if(ois!=null){
					ois.close();
				}
				if(bais!=null){
					bais.close();
				}
			} catch (Exception e2) {
				e2.printStackTrace();
			}
		}
		return cloneObj;
	}
}

測試代碼

public class TestCopy {
	public static void main(String[] args) {
		Food food = new Food();
		food.setName("草");
		Animal animal = new Animal();
		animal.setName("羊");
		animal.setFood(food);
		Animal animal2 = CopyUtil.clone(animal);
		System.out.println("animal動(dòng)物名:"+animal.getName());
		System.out.println("animal食物名:"+animal.getFood().getName());
		System.out.println("animal2動(dòng)物名:"+animal2.getName());
		System.out.println("animal2食物名:"+animal2.getFood().getName());
		//改變animal中food對象的值
		food.setName("樹葉");
		System.out.println("animal動(dòng)物名:"+animal.getName());
		System.out.println("animal食物名:"+animal.getFood().getName());
		System.out.println("animal2動(dòng)物名:"+animal2.getName());
		System.out.println("animal2食物名:"+animal2.getFood().getName());
	}
}

打印結(jié)果如下

animal動(dòng)物名:羊
animal食物名:草
animal2動(dòng)物名:羊
animal2食物名:草
animal動(dòng)物名:羊
animal食物名:樹葉
animal2動(dòng)物名:羊
animal2食物名:草

利用序列化成功的實(shí)現(xiàn)了深復(fù)制。

到此這篇關(guān)于Java實(shí)現(xiàn)對象復(fù)制的方法實(shí)例的文章就介紹到這了,更多相關(guān)Java對象復(fù)制內(nèi)容請搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!

相關(guān)文章

  • 如何用ObjectMapper將復(fù)雜Map轉(zhuǎn)換為實(shí)體類

    如何用ObjectMapper將復(fù)雜Map轉(zhuǎn)換為實(shí)體類

    這篇文章主要介紹了如何用ObjectMapper將復(fù)雜Map轉(zhuǎn)換為實(shí)體類的操作,具有很好的參考價(jià)值,希望對大家有所幫助。如有錯(cuò)誤或未考慮完全的地方,望不吝賜教
    2021-08-08
  • J2EE中的struts2表單細(xì)節(jié)處理

    J2EE中的struts2表單細(xì)節(jié)處理

    這篇文章主要介紹了J2EE中的struts2表單細(xì)節(jié)處理的相關(guān)資料,需要的朋友可以參考下
    2017-06-06
  • Java使用IOC控制反轉(zhuǎn)的三種設(shè)計(jì)模式詳解

    Java使用IOC控制反轉(zhuǎn)的三種設(shè)計(jì)模式詳解

    這篇文章主要為大家詳細(xì)介紹了Java使用IOC控制反轉(zhuǎn)的三種設(shè)計(jì)模式,具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下
    2017-10-10
  • Spring MVC之mvc:resources如何處理靜態(tài)資源

    Spring MVC之mvc:resources如何處理靜態(tài)資源

    這篇文章主要介紹了Spring MVC之mvc:resources如何處理靜態(tài)資源問題,具有很好的參考價(jià)值,希望對大家有所幫助,如有錯(cuò)誤或未考慮完全的地方,望不吝賜教
    2025-03-03
  • Java 并發(fā)編程ArrayBlockingQueue的實(shí)現(xiàn)

    Java 并發(fā)編程ArrayBlockingQueue的實(shí)現(xiàn)

    這篇文章主要介紹了Java 并發(fā)編程ArrayBlockingQueue的實(shí)現(xiàn),文中通過示例代碼介紹的非常詳細(xì),對大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友們下面隨著小編來一起學(xué)習(xí)學(xué)習(xí)吧
    2021-02-02
  • java獲取微信accessToken的方法

    java獲取微信accessToken的方法

    這篇文章主要為大家詳細(xì)介紹了java獲取微信accessToken的方法,具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下
    2019-09-09
  • Spring Boot集成netty實(shí)現(xiàn)客戶端服務(wù)端交互示例詳解

    Spring Boot集成netty實(shí)現(xiàn)客戶端服務(wù)端交互示例詳解

    這篇文章主要給大家介紹了關(guān)于Spring Boot集成netty實(shí)現(xiàn)客戶端服務(wù)端交互的相關(guān)資料,文中通過示例代碼介紹的非常詳細(xì),對大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友們下面隨著小編來一起學(xué)習(xí)學(xué)習(xí)吧
    2018-12-12
  • SpringMVC實(shí)戰(zhàn)案例RESTFul實(shí)現(xiàn)添加功能

    SpringMVC實(shí)戰(zhàn)案例RESTFul實(shí)現(xiàn)添加功能

    這篇文章主要為大家介紹了SpringMVC實(shí)戰(zhàn)案例RESTFul實(shí)現(xiàn)添加功能詳解,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進(jìn)步,早日升職加薪
    2022-05-05
  • 利用MyBatis實(shí)現(xiàn)條件查詢的方法匯總

    利用MyBatis實(shí)現(xiàn)條件查詢的方法匯總

    這篇文章主要給大家介紹了關(guān)于利用MyBatis實(shí)現(xiàn)條件查詢的相關(guān)資料,文中通過示例代碼介紹的非常詳細(xì),對大家的學(xué)習(xí)或者使用MyBatis具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友們下面來一起學(xué)習(xí)學(xué)習(xí)吧
    2020-08-08
  • Java拆箱與裝箱實(shí)例詳解

    Java拆箱與裝箱實(shí)例詳解

    這篇文章主要介紹了Java拆箱與裝箱,結(jié)合實(shí)例形式詳細(xì)分析了Java拆箱與裝箱相關(guān)的數(shù)據(jù)類型轉(zhuǎn)換操作技巧,需要的朋友可以參考下
    2019-11-11

最新評論