Java语言提供的clone()方法、深克…

    所有的Java类都继承自java.lang.Object。事实上,Object类提供一个clone()方法,可以将一个Java对象复制一份。因此在Java中可以直接使用Object提供的clone()方法来实现对象的克隆

    需要注意的是能够实现克隆的Java类必须实现一个标识接口Cloneable,表示这个Java类支持被复制。

如果一个类没有实现这个接口但是调用了clone()方法,Java编译器将抛出CloneNotSupportedException异常。

 

如下代码所示:

class ConcretePrototype implements  Cloneable

{

……

public Prototype  clone()

{

  Object object = null;

  try {

     object = super.clone();

  } catch (CloneNotSupportedException exception) {

     System.err.println("Not support cloneable");

  }

  return (Prototype )object;

}

……

}

     

      一般而言,Java语言中的clone()方法满足:

(1) 对任何对象x,都有x.clone() != x,即克隆对象与原型对象不是同一个对象;

(2) 对任何对象x,都有x.clone().getClass() == x.getClass(),即克隆对象与原型对象的类型一样;

(3) 如果对象xequals()方法定义恰当,那么x.clone().equals(x)应该成立。

      为了获取对象的一份拷贝,我们可以直接利用Object类的clone()方法,具体步骤如下:

(1) 在派生类中覆盖基类的clone()方法,并声明为public

(2) 在派生类的clone()方法中,调用super.clone()

(3)派生类需实现Cloneable接口。

 

深克隆

在深克隆中,无论原型对象的成员变量是值类型还是引用类型,都将复制一份给克隆对象,深克隆将原型对象的所有引用对象也复制一份给克隆对象。

 

Java语言中,如果需要实现深克隆,可以通过序列化(Serialization)等方式来实现。序列化就是将对象写到流的过程,写到流中的对象是原有对象的一个拷贝,而原对象仍然存在于内存中。通过序列化实现的拷贝不仅可以复制对象本身,而且可以复制其引用的成员对象,因此通过序列化将对象写到一个流中,再从流里将其读出来,可以实现深克隆。需要注意的是能够实现序列化的对象其类必须实现Serializable接口,否则无法实现序列化操作。两个类均需要实现Serializable接口。

 

修改后的附件类Attachment代码如下:

 

import  java.io.*;

 

//附件类

class  Attachment implements Serializable

{

       private  String name; //附件名

       public  void setName(String name)

       {

              this.name  = name;

       }

       public  String getName()

       {

              return  this.name;

       }

     public void download()

     {

            System.out.println("下载附件,文件名为" + name);

     }

}

      工作周报类WeeklyLog不再使用Java自带的克隆机制,而是通过序列化来从头实现对象的深克隆,我们需要重新编写clone()方法,修改后的代码如下:

 

import  java.io.*;

 

//工作周报类

class  WeeklyLog implements Serializable

{

       private  Attachment attachment;

       private  String name;

       private  String date;

       private  String content;

       public  void setAttachment(Attachment attachment) {

              this.attachment  = attachment;

       }

       public  void setName(String name) {

              this.name  = name;

       }

       public  void setDate(String date) {

              this.date  = date;

       }

       public  void setContent(String content) {

              this.content  = content;

       }

       public  Attachment getAttachment(){

              return  (this.attachment);

       }

       public  String getName() {

              return  (this.name);

       }

       public  String getDate() {

              return  (this.date);

       }

       public  String getContent() {

              return  (this.content);

       }

   //使用序列化技术实现深克隆

       public WeeklyLog deepClone() throws  IOException, ClassNotFoundException, OptionalDataException

       {

              //将对象写入流中

              ByteArrayOutputStream bao=new  ByteArrayOutputStream();

              ObjectOutputStream oos=new  ObjectOutputStream(bao);

              oos.writeObject(this);

             

              //将对象从流中取出

              ByteArrayInputStream bis=new  ByteArrayInputStream(bao.toByteArray());

              ObjectInputStream ois=new  ObjectInputStream(bis);

              return  (WeeklyLog)ois.readObject();

       }

}

      

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值