atwood-pan

 

06-设计模式——原型模式

设计模式——原型模式

知识点:

  1. Cloneable接口/Pbject#clone方法 详解
  2. 浅拷贝/深拷贝
  3. 序列化机制实现深拷贝

模式定义:

指原型实例指定创建对象的种类,并且通过拷贝(复制)这些原型创建新的对象

LuvR8s.png

应用场景:

当代码不应该依赖于需要复制的对象的具体类时,请使用Prototype模式

优点:

  1. 可以不耦合具体类的情况下克隆对象
  2. 避免重复的初始化代码
  3. 更方便的构建复杂对象

package com.example.designpatterns.prototype;
import cn.hutool.Hutool;
import cn.hutool.core.util.HashUtil;
import lombok.AllArgsConstructor;
import lombok.Data;
import lombok.NoArgsConstructor;
import java.io.*;
/**
* @program: DesignPatterns
* @description: 原型模式
* @author: Coder_Pan
* @create: 2022-04-13 11:12
**/
public class PrototypeTest {
public static void main(String[] args) throws CloneNotSupportedException {
BaseInfo baseInfo = new BaseInfo("ssss");
Product product = new Product("part1", "part2", 3, 4, 5,baseInfo);
Product clone = product.clone();
System.out.println("克隆出来的对象与源对象不相等");
System.out.println(product == clone);
System.out.println(product);
System.out.println(clone);
product.getBaseInfo().setCompanyName("pppp");
System.out.println(product);
System.out.println("依旧存在关联,这样是不对的,需要通过两次拷贝,对引用对象也进行拷贝才正确");
System.out.println(clone);
}
}
@Data
class BaseInfo implements Cloneable,Serializable{
/**
* 实现序列化,如果需要进行持久化操作,必须加版本号
*/
private static final long serialVersionUID = 42L;
private String companyName;
public BaseInfo(String ssss) {
this.companyName = ssss;
}
@Override
protected BaseInfo clone() throws CloneNotSupportedException {
return ((BaseInfo) super.clone());
}
@Override
public String toString() {
return super.hashCode() + "BaseInfo{" +
"companyName='" + companyName + '\'' +
'}';
}
}
/**
* 定义产品实例
*/
@Data
@AllArgsConstructor
@NoArgsConstructor
class Product implements Cloneable,Serializable{
/**
* 实现序列化,如果需要进行持久化操作,必须加版本号
*/
private static final long serialVersionUID = 42L;
private String part1;
private String part2;
private Integer part3;
private Integer part4;
private Integer part5;
private BaseInfo baseInfo;
/**
* V1 - 使用Java中的clone方式实现原型模式
* @return
* @throws CloneNotSupportedException
*/
@Override
protected Product clone() throws CloneNotSupportedException {
//本对象拷贝
Product clone = (Product) super.clone();
//本对象中使用到的对象的拷贝 == > 深拷贝
BaseInfo clone1 = this.baseInfo.clone();
clone.setBaseInfo(clone1);
return clone;
}
/**
* V2 - 通过Java序列化的方式进行拷贝,实现原型模式
* 若想使用序列化操作,则在涉及到拷贝的每个class上都应实现Serializable
* 这个方式由CPU来执行,比较消耗性能,速度比较慢
*
* 不推荐使用.....
* @return
* @throws CloneNotSupportedException
*/
protected Product clone1() throws CloneNotSupportedException {
//1、定义输出流
ByteArrayOutputStream baos = new ByteArrayOutputStream( );
try {
ObjectOutputStream oos = new ObjectOutputStream(baos);
oos.writeObject( this );
} catch (IOException e) {
e.printStackTrace();
}
//拿到输入流对象
ByteArrayInputStream byteArrayInputStream = new ByteArrayInputStream(baos.toByteArray());
//从内存中恢复数据
try {
ObjectInputStream ois = new ObjectInputStream(byteArrayInputStream);
Product product = (Product) ois.readObject();
return product;
//这里完成深拷贝
} catch (IOException e) {
e.printStackTrace();
} catch (ClassNotFoundException e) {
e.printStackTrace();
}
return null;
}
@Override
public String toString() {
return super.hashCode() +
"Product{" +
"part1='" + part1 + '\'' +
", part2='" + part2 + '\'' +
", part3=" + part3 +
", part4=" + part4 +
", part5=" + part5 +
", baseInfo=" + baseInfo +
'}';
}
}

posted on   JavaCoderPan  阅读(12)  评论(0编辑  收藏  举报  

相关博文:
阅读排行:
· 阿里最新开源QwQ-32B,效果媲美deepseek-r1满血版,部署成本又又又降低了!
· SQL Server 2025 AI相关能力初探
· AI编程工具终极对决:字节Trae VS Cursor,谁才是开发者新宠?
· 开源Multi-agent AI智能体框架aevatar.ai,欢迎大家贡献代码
· Manus重磅发布:全球首款通用AI代理技术深度解析与实战指南

导航

统计

点击右上角即可分享
微信分享提示