GoF设计模式:原型模式(Prototype Pattern)—对象的克隆


GoF设计模式:原型模式(Prototype Pattern)—对象的克隆

模式概述

模式定义

我们平时经常进行的两个电脑基本操作:复制和粘贴,快捷键通常为Ctrl+CCtrl+V,通过对已有对象的复制和粘贴,我们可以创建大量的相同对象。如何在一个面向对象系统中实现对象的复制和粘贴呢?原型模式正为解决此类问题而诞生。

原型模式(Prototype Pattern):使用原型实例指定创建对象的种类,并且通过拷贝这些原型创建新的对象。原型模式是一种对象创建型模式。

需要注意的是通过克隆方法所创建的对象是全新的对象,它们在内存中拥有新的地址,通常对克隆所产生的对象进行修改对原型对象不会造成任何影响,每一个克隆对象都是相互独立的。通过不同的方式修改可以得到一系列相似但不完全相同的对象。

模式结构图

原型模式结构图如下所示:

原型模式(Prototype Pattern)——对象的克隆

原型模式结构图中包含如下几个角色:

  • Prototype(抽象原型类):它是声明克隆方法的接口,是所有具体原型类的公共父类,可以是抽象类也可以是接口,甚至还可以是具体实现类。

  • ConcretePrototype(具体原型类):它实现在抽象原型类中声明的克隆方法,在克隆方法中返回自己的一个克隆对象。

  • Client(客户类):让一个原型对象克隆自身从而创建一个新的对象,在客户类中只需要直接实例化或通过工厂方法等方式创建一个原型对象,再通过调用该对象的克隆方法即可得到多个相同的对象。由于客户类针对抽象原型类Prototype编程,因此用户可以根据需要选择具体原型类,系统具有较好的可扩展性,增加或更换具体原型类都很方便。

原型模式的核心在于如何实现克隆方法。

模式伪代码

定义接口的clone()方法,具体原型类(ConcretePrototype)实现克隆方法

public interface Prototype {
    Prototype clone();
}

public class ConcretePrototype implements Prototype {
    //成员属性
    private String attr;

    @Override
    public Prototype clone() {
        ConcretePrototype prototype = new ConcretePrototype();
        prototype.setAttr(this.attr);
        return prototype;
    }

    // 无参构造
    public ConcretePrototype() {

    }

    // 带参构造
    public ConcretePrototype(String attr) {
        this.attr = attr;
    }

    // getter and setter
    public String getAttr() {
        return attr;
    }

    public void setAttr(String attr) {
        this.attr = attr;
    }
}

在客户类中我们只需要创建一个ConcretePrototype对象作为原型对象,然后调用其clone()方法即可得到对应的克隆对象

public static void main(String[] args) {
  Prototype obj1 = new ConcretePrototype("行无际");
  Prototype obj2 = obj1.clone();
}

这是原型模式的通用实现,它与编程语言特性无关,任何面向对象语言都可以使用这种形式来实现对原型的克隆。

模式应用

模式在JDK中的应用

Java语言提供了clone()方法。Cloneable接口是一个标记接口,也就是没有任何内容,定义如下:

/**
 * A class implements the <code>Cloneable</code> interface to
 * indicate to the {@link java.lang.Object#clone()} method that it
 * is legal for that method to make a
 * field-for-field copy of instances of that class.
 * @see     java.lang.CloneNotSupportedException
 * @see     java.lang.Object#clone()
 */
public interface Cloneable {
}

clone()方法是在Object中定义的,而且是protected型的,只有实现了这个Cloneable接口,才可以在该类的实例上调用clone方法,否则会抛出CloneNotSupportExceptionObject中默认的实现是一个浅拷贝,如果需要深拷贝的话,需要自己重写clone方法或者把对象序列化再反序列化得到新对象或借助第三方的库实现深拷贝。

public class Object {
  protected native Object clone() throws CloneNotSupportedException;
}

public class Item implements Cloneable {

    private String name;

    private Object obj;
    
    public static void main(String[] args) throws Exception {
        Item item = new Item("行无际", new Object());
        Item replicaItem = (Item) item.clone();

        // true,表明默认浅拷贝
        System.out.println(item.obj == replicaItem.obj);
    }
}

模式在开源项目中的应用

项目中我们可能会结合一些工具库,如BeanUtils.copyProperties()来实现对象的克隆。这里也就没必要举例子,其实就是把对象的属性等拷贝一份,但是要根据实际需求来决定是深拷贝还是浅拷贝。另外Spring容器中的Beanscope有点这里的味道。

  1. 当bean的scope为singleton时,Spring容器仅创建类的一个实例对象,当下次获取的时候直接返回已创建出来的对象,即单例

  2. 当bean的scope为prototype时,用户每次获取对象时都创建一个全新的对象返回。

模式总结

原型模式作为一种快速创建大量相同或相似对象的方式,在软件开发中应用较为广泛,很多软件提供的复制(Ctrl+C)和粘贴(Ctrl+V)操作就是原型模式的典型应用,下面对该模式的使用效果和适用情况进行简单的总结。

主要优点

当创建新的对象实例较为复杂时,使用原型模式可以简化对象的创建过程,通过复制一个已有实例可以提高新实例的创建效率。

适用场景

(1) 创建新对象成本较大(如初始化需要占用较长的时间,占用太多的CPU资源或网络资源),新的对象可以通过原型模式对已有对象进行复制来获得,如果是相似对象,则可以对其成员变量稍作修改。

(2) 如果系统要保存对象的状态,而对象的状态变化很小,或者对象本身占用内存较少时,可以使用原型模式配合备忘录模式来实现。

(3) 需要避免使用分层次的工厂类来创建分层次的对象,并且类的实例对象只有一个或很少的几个组合状态,通过复制原型对象得到新实例可能比使用构造函数创建一个新实例更加方便。

CSCODE.NET开发框架文库 - C/S架构winform开发框架

CSCODE.NET开发框架文库 - C/S架构Winform开发框架

版权声明:本文为开发框架文库发布内容,转载请附上原文出处连接
C/S框架网
上一篇:GoF设计模式:享元模式(Flyweight Pattern)—实现对象的复用
下一篇:C#的Expression表达式使用方法
评论列表

发表评论

评论内容
昵称:
关联文章

GoF设计模式原型模式(Prototype Pattern)—对象克隆
GoF设计模式:工厂模式(Factory Pattern)
GoF设计模式:享元模式(Flyweight Pattern)—实现对象复用
GoF设计模式:迭代器模式(Iterator Pattern)—遍历聚合对象元素
GoF设计模式:代理模式(Proxy Pattern)—对象间接访问
GoF设计模式:单例模式(Singleton Pattern)—确保对象唯一性
GoF设计模式:建造者模式(Builder Pattern)—复杂对象组装与创建
GoF设计模式:中介者模式(Mediator Pattern)—协调多个对象之间交互
GoF设计模式:访问者模式(Visitor Pattern)—操作复杂对象结构
GoF设计模式:装饰模式(Decorator Pattern)—扩展系统功能
GoF设计模式:职责链模式(Chain of Responsibility Pattern)—请求链式处理
GoF设计模式:组合模式(Composite Pattern)—树形结构处理
GoF设计模式:适配器模式(Adapter Pattern)—不兼容结构协调
GoF设计模式:外观模式(Facade Pattern)—提供统一入口
GoF设计模式:命令模式(Command Pattern)—请求发送者与接收者解耦
GoF设计模式:桥接模式(Bridge Pattern)—处理多维度变化
C#设计模式应用-单件模式(Singleton Pattern)
设计模式 - 外观模式应用(Façade Pattern)
开发应用 - 策略模式(Strategy Pattern) 常用设计模式
C# 克隆对象、复制对象(浅拷贝)、复制对象相同属性

热门标签
.NET5 .NET6 .NET7 APP Auth-软件授权注册系统 Axios B/S B/S开发框架 Bug Bug记录 C#加密解密 C#源码 C/S CHATGPT CMS系统 CodeGenerator CSFramework.DB CSFramework.EF CSFrameworkV1学习版 CSFrameworkV2标准版 CSFrameworkV3高级版 CSFrameworkV4企业版 CSFrameworkV5旗舰版 CSFrameworkV6.0 DAL数据访问层 Database datalock DbFramework Demo教学 Demo下载 DevExpress教程 DOM EF框架 Element-UI EntityFramework ERP ES6 Excel FastReport GIT HR IDatabase IIS JavaScript LINQ MES MiniFramework MIS NavBarControl Node.JS NPM OMS ORM PaaS POS Promise API Redis SAP SEO SQL SQLConnector TMS系统 Token令牌 VS2022 VSCode VUE WCF WebApi WebApi NETCore WebApi框架 WEB开发框架 Windows服务 Winform 开发框架 Winform 开发平台 WinFramework Workflow工作流 Workflow流程引擎 版本区别 报表 踩坑日记 操作手册 代码生成器 迭代开发记录 基础资料窗体 架构设计 角色权限 开发sce 开发技巧 开发教程 开发框架 开发平台 开发指南 客户案例 快速搭站系统 快速开发平台 秘钥 密钥 权限设计 软件报价 软件测试报告 软件简介 软件开发框架 软件开发平台 软件开发文档 软件体系架构 软件下载 软著证书 三层架构 设计模式 生成代码 实用小技巧 收钱音箱 数据锁 数据同步 微信小程序 未解决问题 文档下载 喜鹊ERP 喜鹊软件 系统对接 详细设计说明书 行政区域数据库 需求分析 疑难杂症 蝇量级框架 蝇量框架 用户管理 用户开发手册 用户控件 在线支付 纸箱ERP 智能语音收款机 自定义窗体 自定义组件 自动升级程序