IT数码 购物 网址 头条 软件 日历 阅读 图书馆
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
图片批量下载器
↓批量下载图片,美女图库↓
图片自动播放器
↓图片自动播放器↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁
 
   -> Java知识库 -> 【设计模式】创建型模式——原型模式 -> 正文阅读

[Java知识库]【设计模式】创建型模式——原型模式

原型模式

一、定义

原型模式是一种创建型设计模式。能够复制已有对象, 而又无需使代码依赖它们所属的类。

二、问题

有一个订单系统,当订单中的货品数量大于1000时,那么该系统就会分拆成两个订单,如果还大于1000再拆分……
订单:id,货物名称,数量
货物:id,货物名称

三、解决方案

我们就可以使用克隆来完成对订单的复制。
创建一系列不同类型的对象并不同的方式对其进行配置。 如果所需对象与预先配置的对象相同, 那么你只需克隆原型即可, 无需新建一个对象。
支持克隆的对象即为原型(该问题中为订单)

注意:克隆时需要注意深浅拷贝的问题!
浅拷贝:拷贝基本数据类型 如 id,数量
深拷贝:拷贝引用数据类型 如 货物

四、代码实现

1、原型 (Prototype) 接口将对克隆方法进行声明。 在绝大多数情况下, 其中只会有一个名为 clone克隆的方法。

这里使用的是Java自带的克隆接口

package java.lang;

/**
 * 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.
 * <p>
 * Invoking Object's clone method on an instance that does not implement the
 * <code>Cloneable</code> interface results in the exception
 * <code>CloneNotSupportedException</code> being thrown.
 * <p>
 * By convention, classes that implement this interface should override
 * <tt>Object.clone</tt> (which is protected) with a public method.
 * See {@link java.lang.Object#clone()} for details on overriding this
 * method.
 * <p>
 * Note that this interface does <i>not</i> contain the <tt>clone</tt> method.
 * Therefore, it is not possible to clone an object merely by virtue of the
 * fact that it implements this interface.  Even if the clone method is invoked
 * reflectively, there is no guarantee that it will succeed.
 *
 * @author  unascribed
 * @see     java.lang.CloneNotSupportedException
 * @see     java.lang.Object#clone()
 * @since   JDK1.0
 */
public interface Cloneable {
}

2、具体原型 (Concrete Prototype) 类将实现克隆方法。

package com.atmae.prototype;

/**
 * @Author: Mae
 * @Date: 2022/4/13
 * @Time: 11:57
 * @Description:
 */
public class Order implements Cloneable {

    public Order(Long id, Product product, Integer num) {
        this.id = id;
        this.product = product;
        this.num = num;
    }

    /**
     * 订单id号
     */
    private Long id;
    /**
     * 订单产品
     */
    private Product product;
    /**
     * 产品数量
     */
    private Integer num;


    public Long getId() {
        return id;
    }

    public void setId(Long id) {
        this.id = id;
    }

    public Product getProduct() {
        return product;
    }

    public void setProduct(Product product) {
        this.product = product;
    }

    public Integer getNum() {
        return num;
    }

    public void setNum(Integer num) {
        this.num = num;
    }

    @Override
    public String toString() {
        return "Order{" +
                "id=" + id +
                ", product=" + product +
                ", num=" + num +
                '}'+'\n';
    }

    /**
     * 深拷贝
     * @return 订单对象
     * @throws CloneNotSupportedException 克隆?
     */
    @Override
    protected Object clone() throws CloneNotSupportedException {
        Order order = (Order) super.clone();
        order.product= (Product) this.product.clone();
        return order;
    }
}

3、客户端

package com.atmae.prototype;

import java.util.ArrayList;
import java.util.List;

/**
 * @Author: Mae
 * @Date: 2022/4/13
 * @Time: 13:01
 * @Description: 客户端
 */
public class Client {
    public static void main(String[] args) throws CloneNotSupportedException {
        Product product = new Product("面包", 10001L);
        Order order = new Order(10000L, product, 6600);
        List<Order> orders = new ArrayList<>();
        int num=1;
        while (order.getNum() > 1000) {
            Order o = (Order) order.clone();
            o.setNum(1000);
            o.setId(order.getId()+num);
            order.setNum(order.getNum() - 1000);
            orders.add(o);
            num++;
        }
        orders.add(order);
        System.out.println(orders);
    }
}

在这里插入图片描述

五、UML图

在这里插入图片描述

六、原型模式适用场景

  • 需要复制一些对象, 同时又希望代码独立于这些对象所属的具体类

七、总结

优点

  • 可以克隆对象, 而无需与它们所属的具体类相耦合。
  • 可以克隆预生成原型, 避免反复运行初始化代码。
  • 可以更方便地生成复杂对象。
  • 可以用继承以外的方式来处理复杂对象的不同配置。

缺点

  • 如果克隆引用数据类型,需要递归克隆

八、与其他模式的比较

  • 与工厂方法模式
    原型并不基于继承, 因此没有继承的缺点。 另一方面, 原型需要对被复制对象进行复杂的初始化。
    工厂方法基于继承, 但是它不需要初始化步骤。
    原型可以起到工厂模式的效果。
  Java知识库 最新文章
计算距离春节还有多长时间
系统开发系列 之WebService(spring框架+ma
springBoot+Cache(自定义有效时间配置)
SpringBoot整合mybatis实现增删改查、分页查
spring教程
SpringBoot+Vue实现美食交流网站的设计与实
虚拟机内存结构以及虚拟机中销毁和新建对象
SpringMVC---原理
小李同学: Java如何按多个字段分组
打印票据--java
上一篇文章      下一篇文章      查看所有文章
加:2022-04-14 23:36:51  更:2022-04-14 23:36:54 
 
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁

360图书馆 购物 三丰科技 阅读网 日历 万年历 2024年11日历 -2024/11/24 5:54:56-

图片自动播放器
↓图片自动播放器↓
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
图片批量下载器
↓批量下载图片,美女图库↓
  网站联系: qq:121756557 email:121756557@qq.com  IT数码