欢迎您访问程序员文章站本站旨在为大家提供分享程序员计算机编程知识!
您现在的位置是: 首页

原型设计模式

程序员文章站 2024-03-17 17:36:52
...

定义

用原型模式指定创建对象的种类,并通过复制这些原型创建新的对象。
原型设计模式,是23种设计模式的创建型模式,简单来说,就是对象的克隆。将要被克隆的对象,我们称之为原型。

使用场景

  • 类初始化或new一个新对象时,需要消耗非常多的资源,因为通过原型复制的方式不会执行构造方法,避免了初始化占有的时间和空间。
  • 一个对象需要提供给其他对象访问,而且各个调用者可能都需要修改其值时,可以考虑使用原型模式复制多个对象供调用者使用,即保护性拷贝。

UML类图

原型设计模式

  • Client:客户端角色。
  • Prototype:抽象类或接口,声明具备clone能力。
  • ConcretePrototype:具体的原型类。

代码实现

package com.tcl.tvweishi.middleware;

import java.util.ArrayList;
import java.util.Arrays;

/**
 * 原型模式代码实现
 * <p>
 * WordDocument就是ConcretePrototype,Cloneable就是Prototype
 *
 * @author Agg
 * @date 2020/06/29
 */
public class WordDocument implements Cloneable {

    private String mText; // 模拟Word文档中的文字
    private ArrayList<String> mImages = new ArrayList<>(); // 模拟Word文档中的图片

    public WordDocument() {
        System.out.println("constructed function");
    }

    public String getText() {
        return mText;
    }

    public void setText(String mText) {
        this.mText = mText;
    }

    public ArrayList<String> getImages() {
        return mImages;
    }

    public void setImages(ArrayList<String> mImages) {
        this.mImages = mImages;
    }

    public void showDocument() {
        System.out.println("———————— Start ————————");
        System.out.println("text = " + mText);
        for (String image : mImages) {
            System.out.println("image = " + image);
        }
        System.out.println("———————— End ————————");
    }

    @Override
    protected WordDocument clone() {
        try {
            WordDocument wordDocument = (WordDocument) super.clone();
            wordDocument.mText = this.mText;
//            wordDocument.mImages = this.mImages; // 浅拷贝
            wordDocument.mImages = (ArrayList<String>) this.mImages.clone(); // 深拷贝
            return wordDocument;
        } catch (Exception e) {
            e.printStackTrace();
        }
        return null;
    }

    public static class Client {
        public static void main(String[] args) {
            // 构造原型
            WordDocument wordDocument = new WordDocument();
            wordDocument.setText("Hello World!");
            wordDocument.setImages(new ArrayList(Arrays.asList("image1","image2","image3")));

            // 原型+打印
            wordDocument.showDocument();

            // 拷贝+打印
            WordDocument copyWordDocument = wordDocument.clone(); // 不会调用构造函数
            copyWordDocument.showDocument();

            // 修改+打印
            copyWordDocument.setText("Hello Gold!");
            copyWordDocument.setImages(new ArrayList(Arrays.asList("image4","image5","image6")));
            copyWordDocument.showDocument();

            // 原型+打印
            wordDocument.showDocument();
        }
    }

}
打印:

constructed function
———————— Start ————————
text = Hello World!
image = image1
image = image2
image = image3
———————— End ————————
———————— Start ————————
text = Hello World!
image = image1
image = image2
image = image3
———————— End ————————
———————— Start ————————
text = Hello Gold!
image = image4
image = image5
image = image6
———————— End ————————
———————— Start ————————
text = Hello World!
image = image1
image = image2
image = image3
———————— End ————————

深浅拷贝问题

注意对于非基本数据类型的引用类型的浅拷贝问题,由于指向的同一堆对象内存地址,修改一处后多处引用会存在联动问题。
一般建议原型模式尽量使用深拷贝,避免对原型对象造成副作用。