java中clone的用法_java clone是浅拷贝吗

java中clone的用法_java clone是浅拷贝吗一.Cloneable的用途Cloneable和Serializable一样都是标记型接口,它们内部都没有方法和属性,implementsCloneable表示该对象能被克隆,能使用Object.clone()方法。如果没有implementsCloneable的类调用Object.clone()方法就会抛出CloneNotSupportedException。二.克隆的分类(1)浅克隆(s

大家好,又见面了,我是你们的朋友全栈君。如果您正在找激活码,请点击查看最新教程,关注关注公众号 “全栈程序员社区” 获取激活教程,可能之前旧版本教程已经失效.最新Idea2022.1教程亲测有效,一键激活。

Jetbrains全系列IDE稳定放心使用

一.Cloneable 的用途

Cloneable和Serializable一样都是标记型接口,它们内部都没有方法和属性,implements Cloneable表示该对象能被克隆,能使用Object.clone()方法。如果没有implements Cloneable的类调用Object.clone()方法就会抛出CloneNotSupportedException。

二.克隆的分类

(1)浅克隆(shallow clone),浅拷贝是指拷贝对象时仅仅拷贝对象本身和对象中的基本变量,而不拷贝对象包含的引用指向的对象。
(2)深克隆(deep clone),深拷贝不仅拷贝对象本身,而且拷贝对象包含的引用指向的所有对象。

举例区别一下:对象A1中包含对B1的引用,B1中包含对C1的引用。浅拷贝A1得到A2,A2中依然包含对B1的引用,B1中依然包含对C1的引用。深拷贝则是对浅拷贝的递归,深拷贝A1得到A2,A2中包含对B2(B1的copy)的引用,B2中包含对C2(C1的copy)的引用。

三.克隆的举例

要让一个对象进行克隆,其实就是两个步骤:
1. 让该类实现java.lang.Cloneable接口;
2. 重写(override)Object类的clone()方法。

public class Wife implements Cloneable { 
     
    private int id;  
    private String name;  

    public int getId() {  
        return id;  
    }  

    public void setId(int id) {  
        this.id = id;  
    }  

    public String getName() {  
        return name;  
    }  

    public void setName(String name) {  
        this.name = name;  
    }  

    public Wife(int id,String name) {  
        this.id = id;  
        this.name = name;  
    }  

    @Override  
    public int hashCode() {
  
  //myeclipse自动生成的 
        final int prime = 31;  
        int result = 1;  
        result = prime * result + id;  
        result = prime * result + ((name == null) ? 0 : name.hashCode());  
        return result;  
    }  

    @Override  
    public boolean equals(Object obj) {
  
  //myeclipse自动生成的 
        if (this == obj)  
            return true;  
        if (obj == null)  
            return false;  
        if (getClass() != obj.getClass())  
            return false;  
        Wife other = (Wife) obj;  
        if (id != other.id)  
            return false;  
        if (name == null) {  
            if (other.name != null)  
                return false;  
        } else if (!name.equals(other.name))  
            return false;  
        return true;  
    }  

    @Override  
    public Object clone() throws CloneNotSupportedException {  
        return super.clone();  
    }  

    /** * @param args * @throws CloneNotSupportedException */  
    public static void main(String[] args) throws CloneNotSupportedException {  
        Wife wife = new Wife(1,"wang");  
        Wife wife2 = null;  
        wife2 = (Wife) wife.clone();  
        System.out.println("class same="+(wife.getClass()==wife2.getClass()));//true 
        System.out.println("object same="+(wife==wife2));//false 
        System.out.println("object equals="+(wife.equals(wife2)));//true 
    }  
}  

四.浅克隆的举例

public class Husband implements Cloneable { 
     
    private int id;  
    private Wife wife;  

    public Wife getWife() {  
        return wife;  
    }  

    public void setWife(Wife wife) {  
        this.wife = wife;  
    }  

    public int getId() {  
        return id;  
    }  

    public void setId(int id) {  
        this.id = id;  
    }  

    public Husband(int id) {  
        this.id = id;  
    }  

    @Override  
    public int hashCode() {
  
  //myeclipse自动生成的 
        final int prime = 31;  
        int result = 1;  
        result = prime * result + id;  
        return result;  
    }  

    @Override  
    protected Object clone() throws CloneNotSupportedException {  
        return super.clone();  
    }  

    @Override  
    public boolean equals(Object obj) {
  
  //myeclipse自动生成的 
        if (this == obj)  
            return true;  
        if (obj == null)  
            return false;  
        if (getClass() != obj.getClass())  
            return false;  
        Husband other = (Husband) obj;  
        if (id != other.id)  
            return false;  
        return true;  
    }  

    /** * @param args * @throws CloneNotSupportedException */  
    public static void main(String[] args) throws CloneNotSupportedException {  
        Wife wife = new Wife(1,"jin");  
        Husband husband = new Husband(1);  
        Husband husband2 = null;  
        husband.setWife(wife);  
        husband2 = (Husband) husband.clone();  
        System.out.println("husband class same="+(husband.getClass()==husband2.getClass()));//true 
        System.out.println("husband object same="+(husband==husband2));//false 
        System.out.println("husband object equals="+(husband.equals(husband)));//true 
        System.out.println("wife class same="+(husband.getWife().getClass()==husband2.getWife().getClass()));//true 
        System.out.println("wife object same="+(husband.getWife()==husband2.getWife()));//true 
        System.out.println("wife object equals="+(husband.getWife().equals(husband.getWife())));//true 
    }  
}  

五.深克隆的举例

如果要深克隆,需要重写(override)Object类的clone()方法,并且在方法内部调用持有对象的clone()方法;注意如下代码的clone()方法

public class Husband implements Cloneable { 
     
    private int id;  
    private Wife wife;  

    public Wife getWife() {  
        return wife;  
    }  

    public void setWife(Wife wife) {  
        this.wife = wife;  
    }  

    public int getId() {  
        return id;  
    }  

    public void setId(int id) {  
        this.id = id;  
    }  

    public Husband(int id) {  
        this.id = id;  
    }  

    @Override  
    public int hashCode() {
  
  //myeclipse自动生成的 
        final int prime = 31;  
        int result = 1;  
        result = prime * result + id;  
        return result;  
    }  

    @Override  
    protected Object clone() throws CloneNotSupportedException {  
        Husband husband = (Husband) super.clone();  
        husband.wife = (Wife) husband.getWife().clone();  
        return husband;  
    }  

    @Override  
    public boolean equals(Object obj) {
  
  //myeclipse自动生成的 
        if (this == obj)  
            return true;  
        if (obj == null)  
            return false;  
        if (getClass() != obj.getClass())  
            return false;  
        Husband other = (Husband) obj;  
        if (id != other.id)  
            return false;  
        return true;  
    }  

    /** * @param args * @throws CloneNotSupportedException */  
    public static void main(String[] args) throws CloneNotSupportedException {  
        Wife wife = new Wife(1,"jin");  
        Husband husband = new Husband(1);  
        Husband husband2 = null;  
        husband.setWife(wife);  
        husband2 = (Husband) husband.clone();  
        System.out.println("husband class same="+(husband.getClass()==husband2.getClass()));//true 
        System.out.println("husband object same="+(husband==husband2));//false 
        System.out.println("husband object equals="+(husband.equals(husband)));//true 
        System.out.println("wife class same="+(husband.getWife().getClass()==husband2.getWife().getClass()));//true 
        System.out.println("wife object same="+(husband.getWife()==husband2.getWife()));//false 
        System.out.println("wife object equals="+(husband.getWife().equals(husband.getWife())));//true 
    }  
}  

但是也有不足之处,如果Husband内有N个对象属性,突然改变了类的结构,还要重新修改clone()方法。解决办法:可以使用Serializable运用反序列化手段,调用java.io.ObjectInputStream对象的 readObject()方法。

版权声明:本文内容由互联网用户自发贡献,该文观点仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请联系我们举报,一经查实,本站将立刻删除。

发布者:全栈程序员-站长,转载请注明出处:https://javaforall.net/182060.html原文链接:https://javaforall.net

(0)
全栈程序员-站长的头像全栈程序员-站长


相关推荐

  • Eclipse 汉化教程完美版

    Eclipse 汉化教程完美版1.首先查看自己的Eclipse版本号点来Help中的AboutEclipse,我的是最新版本的Oxygen。2、去官网上找对应的汉化安装包路径浏览器打开网址 http://www.eclipse.org/babel/downloads.php 找到对应自己版本的安装包我的是http://archive.eclipse.org/technology/babel/update-site/R0.15…

    2022年6月5日
    30
  • Echarts 关系图谱示例「建议收藏」

    Echarts 关系图谱示例「建议收藏」<!DOCTYPEhtml><html><head><metaname=”viewport”content=”width=device-width”/><title>ECharts关系图谱</title><scriptsrc=”jquery-1.10.2.min.js”></script><scriptsrc=”echarts.min.js”>.

    2022年6月26日
    29
  • AekdyCoin出过的ACM题「建议收藏」

    AekdyCoin出过的ACM题「建议收藏」以下转载AekdyCoin的Blog,可以用来学习出题者思想。1. Mod Tree  (HDU 1st “Old-Vegetable-Birds Cup” Programming Open Contest )本人出的第一个题目,考察的是扩展Baby-step Giant-step,虽然在比赛时数据比较水,可是依然没有人通过……(200+次提交)PS.此题的PO

    2022年7月23日
    10
  • ajax怎么解决报414,关于c#:HTTP错误414。请求URL太长。 asp.net

    ajax怎么解决报414,关于c#:HTTP错误414。请求URL太长。 asp.net我收到错误”HTTP错误414。请求URL太长”。从下面的文章中,我了解到这是由于查询字符串很长所致:在web.config中,我有maxQueryStringLength=”2097151″。这是最大值吗?为了解决此问题,我应该在web.config中设置maxUrl吗?如果是这样,支持的最大值是多少?我该怎么办才能解决此错误?是否可以将URL中的某些长字符串替换为整数或Guid?如果…

    2022年6月3日
    43
  • java绝对值判断_Java判断绝对值的方法总结[通俗易懂]

    if-else语句判断:importjava.util.Scanner;publicclassAbsoluteValue{publicstaticvoidmain(String[]args){Scannerinput=newScanner(System.in);//声明扫描仪变量System.out.println(“请输入数值”);//系统提示输入try{//监听异常whi…

    2022年4月8日
    84
  • 公网远程开机(唤醒家庭PC)

    公网远程开机(唤醒家庭PC)一、背景前一段搞使用seafile搞了私有云盘,不过不需要的时候开着电脑好像有点浪费,所以就开始了通过公网开机的道路二、关键性问题问题要说在前面,常规性的东西百度一般配置都可以搞定,如果各种面向百度的配置都已经尝试,请注意如下问题。. 一定在被开机的直连路由设备上进行MAC与IP地址绑定(原理略)。局域网直接子网内广播发送可以不用绑定。 被开机的系统需要安装对应的网卡驱动(实验CentOS7是有问题的,windows用驱动精灵安装下网卡驱动搞定)三、通过互联网公网远程开机一般性步骤按照常

    2022年5月30日
    66

发表回复

您的邮箱地址不会被公开。 必填项已用 * 标注

关注全栈程序员社区公众号