原型模式

什么是原型模式?

百科定义:用原型实例指定创建对象的种类,并且通过拷贝这些原型创建新的对象。

通俗的说,就是复制现在的已有对象,来创建新的对象,java对象里的复制粘贴。

实现方式

Object类中提供有本地方法clone,java类只要实现了Cloneable接口,就可以使用clone方法来进行对象的拷贝,使用很简单,下面来看代码:

public class Prototype implements Cloneable {
    public int a;
    public B b = new B();

    // 重写clone方法
    public Object clone() {
        try {
            return super.clone();
        } catch (CloneNotSupportedException e) {
            e.printStackTrace();
        }
        return null;
    }

    class B {   }
    public static void main(String[] args) {
        Prototype prototype = new Prototype();
        prototype.a=2;
        Prototype prototypeClone = (Prototype) prototype.clone();
        System.out.println("原对象:" + prototype);
        System.out.println("克隆对象:" + prototypeClone);
        System.out.println("原对象的属性:" + prototype.a+","+prototype.b);
        System.out.println("克隆对象的属性:" + prototype.a+","+prototypeClone.b);
    }
}

运行结果:

原对象:com.tangh.test.Prototype@7629b854
克隆对象:com.tangh.test.Prototype@2d04cf67
原对象的属性:2,com.tangh.test.Prototype$B@16cc8a48
克隆对象的属性:2,com.tangh.test.Prototype$B@16cc8a48

从结果可以看出,克隆出的对象也是新的对象,但是对象中的B属性却还是指定同一个地址,说明对象中的对象还未克隆,这就是clone方法的弊端了,只是实现了浅拷贝。

浅拷贝:复制对象中的八大基本数据类型和String类型,其他类型只是复制了对象的引用。
深拷贝:复制对象中的所有属性,除八大基本类型和String类型外的其他类型也全复制为新对象,换言之,深拷贝把要复制的对象所引用的对象都复制了一遍。

有了对深拷贝的认识,改良上述例子中的clone方法,如下:

public class Prototype implements Cloneable {
    public int a;
    public B b = new B();

    // 重写clone方法
    public Object clone() {
        try {
            Prototype p = (Prototype) super.clone();
            p.b = (B)b.clone();
            return p;
        } catch (CloneNotSupportedException e) {
            e.printStackTrace();
        }
        return null;
    }

    class B implements Cloneable{   
        public Object clone() {
            try {
                return super.clone();
            } catch (CloneNotSupportedException e) {
                e.printStackTrace();
            }
            return null;
        }
    }
    public static void main(String[] args) {
        Prototype prototype = new Prototype();
        prototype.a=2;
        Prototype prototypeClone = (Prototype) prototype.clone();
        System.out.println("原对象:" + prototype);
        System.out.println("克隆对象:" + prototypeClone);
        System.out.println("原对象的属性:" + prototype.a+","+prototype.b);
        System.out.println("克隆对象的属性:" + prototype.a+","+prototypeClone.b);
    }
}
原对象:com.tangh.test.Prototype@2d04cf67
克隆对象:com.tangh.test.Prototype@16cc8a48
原对象的属性:2,com.tangh.test.Prototype$B@4e8a88a9
克隆对象的属性:2,com.tangh.test.Prototype$B@69123787

使Prototype类中的B对象实现cloneable接口,对b也进行clone,这样,对象中的对象属性也就能实现克隆了。

实现原理

clone方法是由java虚拟机直接复制到内存块中,是对二进制字节码的操作处理。

优点

  1. 由于clone方法是对虚拟机直接复制到内存块执行,所以比new创建对象要快很多。
  2. 向外部隐藏了创建新实例的复杂性,无需知道创建的细节。
  3. 可以在运行时动态的获取对象的类型以及状态,从而创建一个对象。

缺点

  如果一个对象中属性嵌套很复杂,比如map中有list,list中又是对象,那么要实现深度复制,也不是一件简单的事。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值