文章目录

  • 原型介绍
  • 实现
  • 原型模式
  • 原型中拷贝
    • 浅拷贝
    • 深拷贝
      • 使用clone 方式
      • 序列化方式
  • 总结

原型介绍

举个栗子:大话西游里,孙悟空对战牛魔王,孙悟空拔了一个猴毛一吹,变出了一堆“孙悟空”,这些悟空是孙悟空的副本,这就是原型模式,从一个原型中复制出N个副本。

实现

通过java 提供Object 类提供的clone(克隆)方法实现的。克隆把一个类的所有成员变量,包括变量和方法都被复制到一个新的实例中。原型对象需要实现 Cloneable 接口

原型模式

  • 代码
public class WuKong implements Serializable, Cloneable{private String name;private int age;public void skill(){System.out.println("72变,火眼金睛");}get/set...@Overridepublic String toString() {return "WuKong{" +"name='" + name + '\'' +", age=" + age +'}';}@Overrideprotected Object clone() throws CloneNotSupportedException {return super.clone();}
}
  • 测试
public class MainTest {public static void main(String[] args) throws CloneNotSupportedException {WuKong wuKong = new WuKong();wuKong.setName("齐天大圣");wuKong.setAge(500);wuKong.skill();WuKong wuKong1 = (WuKong) wuKong.clone();wuKong1.skill();System.out.println(wuKong + " " + wuKong.hashCode());System.out.println(wuKong1 + " " + wuKong1.hashCode());System.out.println(wuKong == wuKong1);}
}


克隆产生的新的对象

原型中拷贝

以上是原型的基本实现,但是在原型对象中都是基本数据类型,没有引用类型,Object 的克隆只能进行浅拷贝,也就是不会对引用类型之心拷贝,以上原型是不完整,继续改进

浅拷贝

原型类调整下,增加一个引用对象

  • 原型类
public class WuKong implements Serializable, Cloneable{private String name;private int age;private GlodenCudgel glodenCudgel;public void skill(){System.out.println("72变,火眼金睛");}get/set...@Overridepublic String toString() {return "WuKong{" +"name='" + name + '\'' +", age=" + age +", glodenCudgel=" + glodenCudgel +'}';}@Overrideprotected Object clone() throws CloneNotSupportedException {return super.clone();}
}
  • 引用对象
public class GlodenCudgel implements Serializable, Cloneable{private String g_name;private long wget;get/set...@Overridepublic String toString() {return "GlodenCudgel{" +"g_name='" + g_name + '\'' +", wget=" + wget +'}';}@Overrideprotected Object clone() throws CloneNotSupportedException {return super.clone();}
}
  • 测试浅拷贝
public class MainTest {public static void main(String[] args) throws CloneNotSupportedException {WuKong wuKong = new WuKong();GlodenCudgel glodenCudgel = new GlodenCudgel();glodenCudgel.setG_name("如意金箍棒");glodenCudgel.setWget(1888);wuKong.setName("齐天大圣");wuKong.setAge(500);wuKong.setGlodenCudgel(glodenCudgel);WuKong wuKong1 = (WuKong) wuKong.clone();wuKong.skill();wuKong1.skill();System.out.println("原型:"+wuKong + " " + wuKong.hashCode()+" 金箍棒:"+wuKong.getGlodenCudgel().hashCode());System.out.println("克隆:"+wuKong1 + " " + wuKong1.hashCode()+" 金箍棒:"+wuKong1.getGlodenCudgel().hashCode());System.out.println("原型==克隆:"+(wuKong == wuKong1));}
}


原型方法与复制类引种对象hashcode 相同,是同一对象,修改原型中引用对象会修改克隆对象,显然不是我们所希望的,证明了 Clone 是浅拷贝,如何实现深拷贝,两种方式

深拷贝

使用clone 方式

在原型中重写clone 方法,主要是在克隆中对引应用类型进行重新赋值,其他不变


@Overrideprotected Object clone() throws CloneNotSupportedException {WuKong wuKong = (WuKong) super.clone();glodenCudgel = (GlodenCudgel)getGlodenCudgel().clone();return wuKong;}

重新执行测试方法,实现了深拷贝

通过克隆方式实现深拷贝,有弊端,如果有多个引用,需要每个引用类型都需要重新赋值,比较麻烦。另外原型模式需要实现 Cloneable 接口,违背了OCP 原则。

序列化方式

修改原形类,clone 方法不需要,添加一个深度拷贝方法, 其他方法属性保持不变

public Object deepCopy() {ByteArrayOutputStream byteArrayOutputStream = null;ObjectOutputStream objectOutputStream = null;ByteArrayInputStream byteArrayInputStream = null;ObjectInputStream objectInputStream = null;try {//序列化byteArrayOutputStream = new ByteArrayOutputStream();objectOutputStream = new ObjectOutputStream(byteArrayOutputStream);objectOutputStream.writeObject(this);//反序列化byteArrayInputStream = new ByteArrayInputStream(byteArrayOutputStream.toByteArray());objectInputStream = new ObjectInputStream(byteArrayInputStream);Object o = objectInputStream.readObject();return o;} catch (Exception e) {e.printStackTrace();} finally {try {byteArrayInputStream.close();objectInputStream.close();byteArrayOutputStream.close();objectOutputStream.close();} catch (Exception e1) {e1.printStackTrace();}}return null;}
  • 运行测试

总结

原型模式涉及到深拷贝和浅拷贝,尤其是使用到引用类型时,建议使用深度拷贝,深度拷贝使用序列化方式比较简单,推荐使用

java设计模式中—原型模式相关推荐

  1. java设计模式之原型模式和建造者模式的写法(二)

    背景 原型模式和建造者模式属于创建型模式,在开发中经常会用到,那么这两种设计模式是怎么写的呢,下面进行代码演示. 原型模式 原型模式的核心就是复制 package com.example.protot ...

  2. 北京Java培训 | java设计模式之原型模式

    克隆羊问题 现在有一只羊tom,姓名为: tom, 年龄为:1,颜色为:白色,请编写程序创建和tom羊 属性完全相同的10只羊. 传统方式解决克隆羊问题 传统的方式的优缺点 1) 优点是比较好理解,简 ...

  3. java prototype是什么,java设计模式-原型模式(Prototype)

    定义 原型模式属于对象的创建模式.通过给出一个原型对象来指明所有创建的对象的类型,然后用复制这个原型对象的办法创建出更多同类型的对象.这就是原型模式的用意 原型模式的结构 原型模式要求对象实现同一个可 ...

  4. Java设计模式中组合模式是什么/树形结构怎么组合或显示存储,编程怎么实现树形结构

    继续整理记录这段时间来的收获,详细代码可在我的Gitee仓库Java设计模式克隆下载学习使用! 5.7 组合模式 5.7.1 概述 又名整体模式,是用于把一组相似的对象当作一个单一的对象 依据树形结构 ...

  5. 【Java设计模式】原型模式

    ✍ 在软件系统中 , 有些对象的创建过程较为复杂 , 而且有时候需要频繁创建 , 原型模式通过给出一个原型对象来指明所要创建的对象的类型 , 然后用复制这个原型对象的办法创建出更多同类型的对象, 这就 ...

  6. 【Java设计模式】原型模式、建造者模式

    原型模式 概述 用一个已经创建的实例体为原型,通过复制该原型对象来创建一个和原型对象相同的对象. 结构 原型模式包含如下角色: 抽象原型类:规定了具体原型对象必须实现的的clone ()方法. 具体原 ...

  7. java设计模式--2.原型模式

    原型模式的定义与特点 原型(Prototype)模式的定义如下:用一个已经创建的实例作为原型,通过复制该原型对象来创建一个和原型相同或相似的新对象.在这里,原型实例指定了要创建的对象的种类.用这种方式 ...

  8. Java设计模式之原型模式(浅克隆,深克隆)

    一.原型模式: 概述: 创建型模式之一,它通过复制一个已有对象来获取更多相同或相似的对象,可提高对象创建效率,简化创建过程. 原理: 将一个原型对象传给要发动创建的对象(如客户端对象),这个客户端对象 ...

  9. Java设计模式之原型模式

    原型模式(Prototype Pattern)属于对象创建型模式,通过克隆指定原型对象创建新对象. 优点: 效率高:原型模式可以简化创建对象的创建过程,通过克隆一个已有的实例可以提高新实例的创建效率: ...

最新文章

  1. 服务器微信了早上好,微信问候语早上好 微信早上好经典问候语
  2. 设计模式之二:工厂模式
  3. Vue 全家桶 + Express 实现的博客(后端API全部自己手写)
  4. powershell 查看系统设备\device status
  5. link-cut-tree 简单介绍
  6. [论文阅读] End-to-End Incremental Learning
  7. Atitit 初级 中级 高级 软件工程师的区别 非功能性需求 目录 1. 初级 业务功能 1 1.1. 中级 独立完成业务功能 已经非常见api功能 更加广阔 1 2. 高级 非功能性需求
  8. python入门环境准备_python入门 之 环境配置(一)
  9. Android 开机logo支持的格式
  10. 数据库的常用操作语句
  11. JAVA实验三(南邮)
  12. Oracle和MySQL新增只有查询权限用户
  13. 微服务下权限校验方案
  14. git问题:You have not concluded your merge (MERGE_HEAD exists)
  15. 音频原始数据能量检测算法
  16. 使用Visual Leak Detector工具检测内存泄漏
  17. ENVI系列--安装扩展工具的两种方法
  18. `英语` 2022/8/18
  19. PMP知识点:项目管理十大知识领域和47个过程
  20. 基于Flink打造实时计算平台为企业赋能

热门文章

  1. MSI_MSI-X中断之体验与使用
  2. SpringMVC源码学习
  3. python快速排名seo代码_python打造seo必备工具-自动查询排名
  4. 贝尔曼-福特算法(Bellman-Ford)
  5. 微信公众号--设备功能---添加产品----微信硬件授权
  6. 棠玥寕在剧组被拍,典雅古装照流出!
  7. 推荐几款可以直接在手机上编程的app(包含Java、C、Python等)
  8. 中专计算机专业execl教案,计算机专项目化教案(EXCEL教案
  9. allegro加泪滴方法
  10. Verilog编程规范——reset