前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >【设计模式-原型模式】

【设计模式-原型模式】

作者头像
Liusy
发布2020-09-01 16:22:41
3150
发布2020-09-01 16:22:41
举报
文章被收录于专栏:Liusy01

有些场景中,存在大量相同或相似对象的创建问题,如果用传统的构造函数来创建对象,会比较复杂且耗时耗资源,用原型模式生成对象就很高效。

比如王者里面的小兵,只需创建一个小兵的原型,之后就只需要进行克隆复制就行了。

一、定义

原型实例指定创建对象的种类,并且通过拷贝这些原型创建新的对象。原型类必须实现cloneable接口,实现clone方法。

二、实例

创建一个小兵的原型

代码语言:javascript
复制
public class BatmanPrototype implements Cloneable{

    //横坐标
    private double x;
    //纵坐标
    private double y;
    //血量
    private Blood blood;
    
    //省略get/set方法
    
    @Override
    protected Object clone() throws CloneNotSupportedException {
        return super.clone();
    }
}

1、血量没有实现Cloneable方法
public class Blood{
    private int blood;
}

测试类:

代码语言:javascript
复制
BatmanPrototype batmanPrototype = new BatmanPrototype();
batmanPrototype.setX(10d);
batmanPrototype.setY(10d);
batmanPrototype.setBlood(new Blood(100));

BatmanPrototype cloneObject = (BatmanPrototype) batmanPrototype.clone();
System.out.println("prototype:"+batmanPrototype);
System.out.println("clone:"+cloneObject);

1、修改原型血量
batmanPrototype.getBlood().setBlood(99);

System.out.println("=======================================");

System.out.println("prototype:"+batmanPrototype);
System.out.println("clone:"+cloneObject);

结果如下:

我在代码中只修改了原型的血量,但是从结果看,克隆出来的类的血量也被修改了,这就是浅克隆,只是简单的将地址赋值给了对象,只要原型一变,克隆对象也会改变。

概念:

浅克隆:创建一个新对象,新对象的属性和原来对象完全相同,对于非基本类型属性,仍指向原有属性所指向的对象的内存地址。

深克隆:创建一个新对象,属性中引用的其他对象也会被克隆,不再指向原有对象地址。

那么如何使用深克隆呢?

这就需要重写原型的clone方法以及原型属性需要实现Cloneable接口。

代码语言:javascript
复制
public class BatmanPrototype implements Cloneable{

    //横坐标
    private double x;
    //纵坐标
    private double y;
    //血量
    private Blood blood;

    @Override
    protected Object clone() throws CloneNotSupportedException {
        BatmanPrototype batmanPrototype = (BatmanPrototype) super.clone();
        batmanPrototype.blood = (Blood) this.blood.clone();
        return batmanPrototype;
    }
}

public class Blood implements Cloneable{
    private int blood;

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

再用之前的测试类进行测试:

代码语言:javascript
复制
BatmanPrototype batmanPrototype = new BatmanPrototype();
batmanPrototype.setX(10d);
batmanPrototype.setY(10d);
batmanPrototype.setBlood(new Blood(100));

BatmanPrototype cloneObject = (BatmanPrototype) batmanPrototype.clone();
System.out.println("prototype:"+batmanPrototype);
System.out.println("clone:"+cloneObject);

1、修改原型血量
batmanPrototype.getBlood().setBlood(99);

System.out.println("=======================================");

System.out.println("prototype:"+batmanPrototype);
System.out.println("clone:"+cloneObject);

结果:

此时克隆对象的血量就不会随着原型变化而变化了。

三、源码实例

实现了Cloneable的接口都属于这种模式。

本文参与 腾讯云自媒体同步曝光计划,分享自微信公众号。
原始发表:2020-03-13,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 Liusy01 微信公众号,前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体同步曝光计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档