object方法_日常-Object的Clone方法分析

创建对象的三种方式:

  1. 使用new创建对象 [将地址值存储到堆中,会出现OOM]
  2. 使用反射的方式创建对象 [不安全]
  3. 使用Object类中自带的clone方法

如何使用clone呢?

  • 第一步在对象类中实现Cloneable接口 [标识符]

41a72c8034525b4df2c16d4e53154842.png
  • 第二步在对象类中重写clone方法

a57361982456af1b41f676f562ab2ab1.png
  • 第三步创建对象调用clone方法

d30065ad6967f91a21e8326f7860aaa4.png

ae769eff02ae72fb27edd91bc3d0140e.png
  • 浅拷贝 [Java中默认的就是浅拷贝]

c3d003165416dd85e94aa7bec768158f.png

clone出来的对象不一样,但是其中的成员变量中对象是同一个 [所为的浅拷贝]

存在的危害:

因为里面的成员变量对象地址是一样的,如果修改其中的成员变量的属性值的话,

两个对象的值都会发生变化

建议:

如果需要使用拷贝方法,建议使用深拷贝

  • 深拷贝
  1. 将CloneModel类中的 Student类 也实现Cloneable方法,并且加强其中的clone方法
public class Student  implements Cloneable {
    private String name;

    private int age;

    public Student(String name, int age) {


        this.name = name;
        this.age = age;
    }


    @Override
    public String toString() {
        return "CloneModel{" +
                "name='" + name + ''' +
                ", age=" + age +
                '}';
    }


    @Override
    public Student clone() throws CloneNotSupportedException {
        //从Object类中 强制转换成 Student类
        return (Student)super.clone();
    }
    
   /* @Override
    protected Object clone() throws CloneNotSupportedException {
        return super.clone();
    }*/

}

2.加强CloneModel类中的clone方法

public class CloneModel implements Cloneable {

    private String name;
    private int age;

    private Student student;


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

    public void setAge(int age) {
        this.age = age;
    }

    public void setStudent(Student student) {
        this.student = student;
    }

    public CloneModel(String name, int age) {
        this.name = name;
        this.age = age;
    }


    public CloneModel(String name, int age, Student student) {
        this.name = name;
        this.age = age;
        this.student = student;
    }

    @Override
    public String toString() {
        return "CloneModel{" +
                "name='" + name + ''' +
                ", age=" + age +
                '}';
    }


    @Override
    public CloneModel clone() throws CloneNotSupportedException {
        //继承父类方法,并且进行强制转化
        CloneModel clone = (CloneModel) super.clone();
        clone.setStudent(student.clone());
        return clone;
    }

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

    public static void main(String[] args) throws CloneNotSupportedException {

    /*    CloneModel cloneModel = new CloneModel("无敌", 12);
        //除了  使用 new 创建对象  以及反射创建对象   还可以使用  Object 中的clone方法
        System.out.println("hash值:" + cloneModel.hashCode() + "---" + cloneModel);
        CloneModel clone = (CloneModel) cloneModel.clone();
        System.out.println("hash值:" + clone.hashCode() + "---" + clone);*/

/*
        System.out.println("-------------------------------------");

        //浅拷贝
        CloneModel cloneModel1 = new CloneModel("浅拷贝", 123, new Student("angle", 13));
        System.out.println(cloneModel1 + "---自己的hash值" + "t" + cloneModel1.hashCode() + "t" + "成员变量中的hash值" + "t" + cloneModel1.student.hashCode());
        CloneModel clone1 = (CloneModel) cloneModel1.clone();
        System.out.println(clone1 + "---自己的hash值" + "t" + clone1.hashCode() + "t" + "成员变量中的hash值" + "t" + clone1.student.hashCode());*/


        System.out.println("-------------------------------------");
        //深拷贝
        CloneModel cloneModel2 = new CloneModel("浅拷贝", 123, new Student("angle", 13));
        System.out.println(cloneModel2 + "---自己的hash值" + "t" + cloneModel2.hashCode() + "t" + "成员变量中的hash值" + "t" + cloneModel2.student.hashCode());
        CloneModel clone = cloneModel2.clone();
        System.out.println(clone + "---自己的hash值" + "t" + clone.hashCode() + "t" + "成员变量中的hash值" + "t" + clone.student.hashCode());

    }
}


3.测试数据

912851461cf1b240e560192345d0f5fe.png

320e18acef8c38401d84934ea8b1b746.png

总结:

如果需要使用到clone的话,使用深拷贝

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值