[设计模式] ------ 原型模式(浅拷贝和深拷贝)

原型模式

原型模式就是使用复制对象,创建出新的对象,并且不需要知道创建的细节(比如类的属性的赋值等等)。

基本使用(浅拷贝)

常见的就是使用Object的clone方法。需要让类实现Cloneable并重写clone方法,才能使用。

public class A implements Cloneable{private String code;private String name;public A(String code, String name) {this.code = code;this.name = name;}public void setCode(String code) {this.code = code;}@Overridepublic Object clone() throws CloneNotSupportedException {return super.clone();}public static void main(String[] args) throws CloneNotSupportedException {A a = new A("00","name1");A a1 = (A)a.clone();a1.setCode("01");A a2 = (A)a.clone();a2.setCode("02");System.out.println(a.hashCode());System.out.println(a1.hashCode());System.out.println(a2.hashCode());}
}

结果,很明显,三个对象是不一样的。

596512129
824318946
930990596

深拷贝

上面那种方式,是浅拷贝,即只能拷贝A类中的基本数据类型和String。对于A类中如果还有其他引用类型,浅拷贝是实现不了引用类型的拷贝的。
所以,需要进行对A深拷贝B,通常有两种方法(重写Clone方法和序列化)。

方法1、重写A的clone方法,并在方法中对B进行拷贝(当然B类中也要实现浅拷贝)。

public class B implements Serializable,Cloneable{private String id;@Overridepublic Object clone() throws CloneNotSupportedException {return super.clone();}
}
public class A implements Serializable,Cloneable{private String code;private String name;private B b;public A(String code, String name, B b) {this.code = code;this.name = name;this.b = b;}public void setCode(String code) {this.code = code;}@Overridepublic Object clone() throws CloneNotSupportedException {A a = (A)super.clone();// 在A的clone方法中,对A的B引用进行clonea.b = (B)a.b.clone();return a;}public static void main(String[] args) throws CloneNotSupportedException {A a = new A("00","name1",new B());A a1 = (A)a.clone();a1.setCode("01");A a2 = (A)a.clone();a2.setCode("02");System.out.println(a.b.hashCode());System.out.println(a1.b.hashCode());System.out.println(a2.b.hashCode());}
}
执行结果:
596512129
824318946
930990596

看执行结果,每个A实例的B引用,都是不同的hashCode值,说明A中的B也被拷贝了。
如果将A中clone方法中的a.b = (B)a.b.clone();注释掉,可以得到最终打印出来的三个结果就是一样的。

方法2、序列化

序列化前提,A和B都要实现Serializable接口。
A和B的定义还是和方法1一样,我们只重写A中的clone方法。

@Overridepublic Object clone() throws CloneNotSupportedException {ByteArrayOutputStream bos = null;ObjectOutputStream oos = null;ByteArrayInputStream bis = null;ObjectInputStream ois = null;try {//序列化,以对象的方式输出去bos = new ByteArrayOutputStream();oos = new ObjectOutputStream(bos);oos.writeObject(this);//反序列化,再以对象的方式写回来,所有的引用类型自然都会带上了bis = new ByteArrayInputStream(bos.toByteArray());ois = new ObjectInputStream(bis);A copyResult = (A)ois.readObject();return copyResult;} catch (Exception e) {e.printStackTrace();}finally {try {bos.close();oos.close();bis.close();ois.close();} catch (IOException e) {e.printStackTrace();}}return null;}

最终效果也是随着A的clone,A中的B引用也被clone出新的一份来了。
上面的这个序列化只是一种实现思路,也可以用fastjson将A对象转成json字符串,再反转成A返回去,其实原理都是一样的。

实际应用场景

其实很好找,只要找到哪些类实现了Cloneable接口,大概率就是用到了所谓了原型模式。

比如Spring的Bean的创建,我都都知道默认是单例模式,那其实还可以知道Bean是多例的,这个就用到了原型模式。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/499760.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

机器学习笔记(了解)

1、概念 机器学习,就是通过历史数据找出一定的规律,并使用这些规律对将来不确定的场景进行决策。 机器学习VS数据分析 数据分析,是人为的从历史交易数据中找规律,从而决策。 机器学习,是机器使用算法,从…

机器学习笔记(常见算法)

C4.5 属于决策树算法,既可以解决分类问题,也可以解决回归问题,属于有监督算法。 现在基本不用这个算法了。 K-Means 属于聚类算法,属于无监督算法 SVM(*) 支持向量机。 曾经一度认为是分类效果最好的算…

赶紧看一下mysql8.0版本的新特性,你的数据库是不是该升级了

这里写目录标题前言mysql8.0的新特性1、账户安全2、优化器索引2.1、隐藏索引(invisible)2.2、降序索引2.3、函数索引3、SQL语句增强4、新增数据分析函数5、InnoDB增强5.1、优化了一些元数据文件5.2、将系统表mysql和数据字典表,全部改为InnoD…

ThreadLocal不仅要应付面试,更要真的理解,真的会用

前言 记得我几年前第一次面试的时候,就是被问了这个,记得面试官直接就让我说说ThreadLocal的实现原理以及平时有没有见过哪些地方用到了。 我当时初入职场,还是一个大菜鸟,所以直接就被干蒙了,至今还记忆犹新。 闲来…

秒杀业务的基础点

秒杀的是一个很常见的业务了。就是在某个时刻,让大量用户抢购少量的优惠的商品,从而达到商品曝光和电商网站的曝光,增大用户流量,从而提升整体销售额。 比如今年疫情下,各大电商网站,就针对口罩开展了秒杀…

随想,产品思维和开发思维

有时候,产品思维和开发思维,由于出发点的不同,会产生较大的分歧。 作为一个开发,不仅要有自己的思维,也要了解产品的思维,这样才能在和产品的撕逼的战斗中所向披靡,百战百胜。 举个例子&#x…

Base64编码的原理与常用实现

这篇主要是为了后面好介绍加密算法,做的铺垫。 这个是基础,什么是一个程序员的涵养,这些基础就是涵养。 平时可能用不到,但必须得会。 如果连这个原理都说不上来,就别玩王者荣耀绝地求生英雄联盟和平精英了&#xff0c…

MD5算法原理与常用实现

目录定义MD5特点常见应用场景1、校验文件的完整性2、存储用户密码原理1、填补信息2、拿到初始值3、真正的计算MD5为什么不可逆java实现和使用定义 MD全称Message-Digest,即信息摘要,所以MD家族的算法也叫信息摘要算法 MD家族有MD2、MD3、MD4、MD5&#…

SHA算法原理与常用实现

看本文前,最好先看看之前的这一篇关于MD5算法的介绍。 MD5算法原理与常用实现 本文目录定义MD5和SHA-1的碰撞问题常见应用场景1、类似MD5的应用场景2、比特币3、https签名算法会用到SHA-256算法原理1、填补信息2、拿到初始值3、真正的计算java实现和使用定义 SHA算…

MAC算法原理与常用实现

看本文前,最好先看看之前的对于MD5算法和SHA算法的介绍。 本文目录定义常见应用场景1、linux客户端:SecureCRT2、Google身份验证器3、银联pos机终端原理java实现和使用定义 MAC(Message Authentication Codes),是一种…

对称加密算法原理与常用实现

目录定义常用对称加密算法DES3DESAESPEB常用对称加密算法的java实现DES实现3DES实现AES实现PEB实现定义 原文通过加密秘钥生成密文,密文通过解密秘钥得到原文。 对于加密秘钥和解密秘钥是相同的算法,就叫对称加密算法。 常用对称加密算法 DES Data E…

面试 HTTP ,99% 的面试官都爱问这些问题

HTTP 和 HTTPS 的区别HTTP 是一种 超文本传输协议(Hypertext Transfer Protocol),HTTP 是一个在计算机世界里专门在两点之间传输文字、图片、音频、视频等超文本数据的约定和规范HTTP 主要内容分为三部分,超文本(Hypertext)、传输…

非对称加密算法 --- RSA签名算法

目录RSA原理RSA应用场景RSA加密场景RSA签名场景RSA加解密和签名算法的java实现RSA原理 通过一定的规则,生成公钥和私钥,公钥和私钥总是成对出现。 公钥可以公开出去,任何人都可以知道。 私钥只有自己知道。 RSA算法能保证,公钥加…

@JsonFormat失效解决

先说结论 JsonFormat失效,换成JSONField就好了 问题经过和原理 JsonFormat作为Date类型的属性值,返回前端格式化处理,很方便。 比如: JsonFormat(pattern "yyyy/MM/dd HH:mm:ss")private Date updateTime;返回给前端…

如何在摆摊经济中脱颖而出

最近,摆摊经济开始火了起来,于是各路诸侯纷纷举起大旗开始摆摊。我周围也不乏有亲朋好友蠢蠢欲动,有的甚至已经初有规模。但这波摆摊风是否真的可行,对谁可行,有哪些风口,有哪些坑,我们慢慢分析…

java 实现 生成短链接服务

java实现短链接转换服务 类似上图这种短信,对应的就是一个短链接。 看到原理也不难,于是先写个最简易版的玩玩,以后有需求了再补充吧 下面是一个简易版的短链接生成代码 搭个spring-boot服务,复制这两个controller,就…

[转载] --- Fastjson1.2.68版及以下全版本远程代码执行漏洞通告

再这样&#xff0c;真的要放弃fastjson了 【安全通告】Fastjson <1.2.68全版本远程代码执行漏洞通告 尊敬的腾讯云用户&#xff0c;您好&#xff01;近日&#xff0c;腾讯云安全运营中心监测到&#xff0c;Fastjson <1.2.68版本存在远程代码执行漏洞&#xff0c;漏洞被利…

[记录] --- safari浏览器对于yyyy-MM的坑

问题 后端给前端返回的带格式的日期类型时&#xff0c;很多时候都是yyyy-MM-dd格式的&#xff0c;在一般浏览器中都没问题&#xff0c;但safari浏览器就会出问题。 解决&#xff1a; 换成yyyy/MM/dd格式

数据库选型经验汇总

数据库选型 下面这些都是免费开源的。 暂且不考虑数据量&#xff0c;大致的选型方案。 一般分析型数据库&#xff0c;都是可以支持GB到TB级别。 上面的分类都不是一定的&#xff0c;只是大体上的推荐。具体还得结合实际场景调整。 数据处理大致可以分成两大类&#xff1a; 联…

excel导出经验

excel导出经验&#xff0c;供参考 数据量&#xff1a;1万以下 直接导出&#xff0c;正常在5秒内 数据量&#xff1a;1万-10万 直接导出&#xff0c;正常在10秒内 数据量&#xff1a;超过10万&#xff0c;建议多文件导出。 可使用多线程查询&#xff0c;比如一个线程查1万…