对原型模式的理解

目录

  • [一、原型模式 vs. 传统的复制对象](#一、原型模式 vs. 传统的复制对象)
    • 1、传统的复制对象
    • 2、原型模式
      • [2.1 原型模式是什么?](#2.1 原型模式是什么?)
      • [2.2 如何实现呢?(原型模式的思想)](#2.2 如何实现呢?(原型模式的思想))
      • [2.3 对原型的理解](#2.3 对原型的理解)
      • [2.4 示例](#2.4 示例)
        • [2.4.1 示例1:Java 的 Cloneable (可克隆) 接口就是立即可用的原型模式](#2.4.1 示例1:Java 的 Cloneable (可克隆) 接口就是立即可用的原型模式)
        • [2.4.2 示例2:克隆时,用户没传入具体的类](#2.4.2 示例2:克隆时,用户没传入具体的类)

一、原型模式 vs. 传统的复制对象

  • 第一次看到原型模式这个名字时,我是懵逼的。这是啥意思啊?
  • 看了相关介绍后,我更懵逼了,这原型模式不就是复制对象吗?这也能算一种设计模式?

1、传统的复制对象

  • 传统的复制对象:必须new一个属于相同类的对象。 然后,必须遍历原始对象的所有成员变量, 并将成员变量值复制到新对象中。
java 复制代码
// 示例
public class User {
    @Getter
    @Setter
    private String name;

    @Setter
    private String ak;

    @Setter
    @Getter
    private String sk;
}

public class UserService {
    public void doProcess(User user) {
        // 要求拷贝user
        User copyedUser = new User();

        copyedUser.setName(user.getName());
        copyedUser.setSk(user.getSk());
//        copyedUser.setAk(user.getAk()); // 错误
    }
}
  • 这里有个小问题: 有些对象可能拥有私有成员变量, 它们在对象本身以外是不可见的(如User的ak字段)。
  • 传统的复制还有另外一个问题必须知道对象所属的类才能创建复制品, 所以代码必须依赖该类
  • 还可能有另外一个问题: 有时只知道对象所实现的接口, 而不知道其所属的具体类, 比如向方法的某个参数传入实现了某个接口的任何对象。
java 复制代码
public void execute(IBuy user) {
        
}

2、原型模式

2.1 原型模式是什么?

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

2.2 如何实现呢?(原型模式的思想)

  • 原型模式将克隆过程委派给被克隆的实际对象(让传入的对象自身具有克隆能力,调用该对象的克隆(clone)方法,即可完成克隆)。
    • 在clone方法中,(1)由于知道自己所属的类,自然可以轻轻松松new一个当前类的对象。(2)由于类中的方法也能访问自己的私有成员变量,因此,可以毫无阻力的将原始对象所有的成员变量值复制到新建对象中。【原型模式解决了传统复制对象的3个问题

2.3 对原型的理解

  • 原型 并不是计算机的独有概念,而是生活中的常见概念。当一个产品原型被验证是成功的,后续会被大量复制,并被销售到全国。因此,原型的本质就是被复制。
    • 支持克隆(被复制)的对象即为原型。

2.4 示例

2.4.1 示例1:Java 的 Cloneable (可克隆) 接口就是立即可用的原型模式
java 复制代码
@ToString
public class User implements Cloneable {
    @Getter
    @Setter
    private String name;

    @Setter
    private String ak;

    @Setter
    @Getter
    private String sk;

    @Override
    public User clone() {
        try {
            return (User) super.clone();
        } catch (CloneNotSupportedException e) {
            throw new AssertionError();
        }
    }
}

public class Application {
    public static void main(String[] args) {
        User user = new User();
        user.setName("张三");
        user.setAk("123456");
        user.setSk("654321");

        User clonedUser = user.clone();
        System.out.println(clonedUser);
    }
}

/**
User(name=张三, ak=123456, sk=654321)
*/
  • Cloneable仅仅是一个用于标识的接口,里面啥都没有。
java 复制代码
public interface Cloneable {
}
  • Object提供了clone方法
java 复制代码
protected native Object clone() throws CloneNotSupportedException;
  • 一个类想用Object的clone()方法,那么就必须实现Cloneable接口,否则会抛异常:CloneNotSupportedException。
2.4.2 示例2:克隆时,用户没传入具体的类
java 复制代码
public abstract class Shape implements Cloneable {
    @Override
    public Shape clone() throws CloneNotSupportedException {
        return (Shape) super.clone();
    }
}

@Data
public class Circle extends Shape {
    /**
     * 半径
     */
    private int radius;
}

@Data
public class Rectangle extends Shape {
    private int width;
    private int height;
}

public class Application {
    public static void main(String[] args) {
        Circle circle = new Circle();
        circle.setRadius(10);

        Rectangle rectangle = new Rectangle();
        rectangle.setHeight(15);
        rectangle.setWidth(5);

        List<Shape> shapes = new ArrayList<>();
        shapes.add(circle);
        shapes.add(rectangle);

        shapes.stream().forEach(shape -> {
            try {
                Shape clonedShape = shape.clone();
                System.out.println(clonedShape);
            } catch (CloneNotSupportedException e) {
                throw new RuntimeException(e);
            }
        });
    }
}
  • 即使没传入具体的类(Shape是抽象类),也能完成克隆。
相关推荐
冰糖雪梨dd14 小时前
JS中new的过程发生了什么
开发语言·javascript·原型模式
white-persist4 天前
SQL 注入详解:从原理到实战
前端·网络·数据库·sql·安全·web安全·原型模式
white-persist4 天前
Python实例方法与Python类的构造方法全解析
开发语言·前端·python·原型模式
魔云连洲7 天前
深入解析:Object.prototype.toString.call() 的工作原理与实战应用
前端·javascript·原型模式
white-persist8 天前
Burp Suite模拟器抓包全攻略
前端·网络·安全·web安全·notepad++·原型模式
青草地溪水旁8 天前
第五章:原型模式 - 克隆大法的大师
c++·设计模式·原型模式
white-persist8 天前
【burp手机真机抓包】Burp Suite 在真机(Android and IOS)抓包手机APP + 微信小程序详细教程
android·前端·ios·智能手机·微信小程序·小程序·原型模式
XiaoLeisj13 天前
【SpringAI】第四弹:深入解析 Rag 检索增强工作流程、最佳实践和调优
阿里云·原型模式·rag·spring ai·灵积大模型
CoderIsArt14 天前
四种对象型创建模式:抽象工厂、 build模式、原型ProtoType与单例模式
单例模式·原型模式
Misnearch15 天前
原型模式了解
原型模式