diff --git a/src/main/java/top/fjy8018/designpattern/pattern/creational/prototype/after/AMail.java b/src/main/java/top/fjy8018/designpattern/pattern/creational/prototype/after/AMail.java new file mode 100644 index 0000000..ecb584a --- /dev/null +++ b/src/main/java/top/fjy8018/designpattern/pattern/creational/prototype/after/AMail.java @@ -0,0 +1,55 @@ +package top.fjy8018.designpattern.pattern.creational.prototype.after; + +import lombok.Getter; +import lombok.Setter; +import lombok.extern.slf4j.Slf4j; + +/** + * 原型模式:使用原型实例指定待创建对象的类型,并且通过复制这个原型来创建新的对象 + * 适用于初始化对象复杂的场景 + *
+ * 邮件 + * + * @author F嘉阳 + * @date 2018-09-25 20:39 + */ +@Slf4j +@Getter +@Setter +public class AMail implements Cloneable { + + private String name; + private String emailAddress; + private String content; + + public AMail() throws InterruptedException { + // 模拟调用构造器需要复杂过程 + Thread.sleep(100); + log.debug(this.getClass().getSimpleName() + "构造器调用"); + } + + /** + * 带上父类toString方法查看是否为同一个对象 + * + * @return + */ + @Override + public String toString() { + return "AMail{" + + "name='" + name + '\'' + + ", emailAddress='" + emailAddress + '\'' + + ", content='" + content + '\'' + + '}'; + } + + /** + * 调用克隆函数不需要调用构造器以此加快实例化速度 + * + * @return + * @throws CloneNotSupportedException + */ + @Override + public Object clone() throws CloneNotSupportedException { + return super.clone(); + } +} diff --git a/src/main/java/top/fjy8018/designpattern/pattern/creational/prototype/after/AMailUtil.java b/src/main/java/top/fjy8018/designpattern/pattern/creational/prototype/after/AMailUtil.java new file mode 100644 index 0000000..56ad395 --- /dev/null +++ b/src/main/java/top/fjy8018/designpattern/pattern/creational/prototype/after/AMailUtil.java @@ -0,0 +1,23 @@ +package top.fjy8018.designpattern.pattern.creational.prototype.after; + +import lombok.extern.slf4j.Slf4j; + +import java.text.MessageFormat; + +/** + * 邮件发送类 + * + * @author F嘉阳 + * @date 2018-09-25 20:42 + */ +@Slf4j +public class AMailUtil { + public static void sendEmail(AMail mail) { + String content = "向{0}同学,邮件地址:{1},邮件内容:{2}发送邮件成功"; + log.info(MessageFormat.format(content, mail.getName(), mail.getEmailAddress(), mail.getContent())); + } + + public static void saveOriginMail(AMail mail) { + log.info("存储Mail记录,originMailContent:{}", mail.getContent()); + } +} diff --git a/src/main/java/top/fjy8018/designpattern/pattern/creational/prototype/before/BMail.java b/src/main/java/top/fjy8018/designpattern/pattern/creational/prototype/before/BMail.java new file mode 100644 index 0000000..3ac771c --- /dev/null +++ b/src/main/java/top/fjy8018/designpattern/pattern/creational/prototype/before/BMail.java @@ -0,0 +1,39 @@ +package top.fjy8018.designpattern.pattern.creational.prototype.before; + +import lombok.Getter; +import lombok.Setter; +import lombok.extern.slf4j.Slf4j; + +/** + * 原型模式:使用原型实例指定待创建对象的类型,并且通过复制这个原型来创建新的对象 + * 适用于初始化对象复杂的场景 + *
+ * 邮件 + * + * @author F嘉阳 + * @date 2018-09-25 20:39 + */ +@Slf4j +@Getter +@Setter +public class BMail { + + private String name; + private String emailAddress; + private String content; + + public BMail() throws InterruptedException { + // 模拟调用构造器需要复杂过程 + Thread.sleep(100); + log.debug(this.getClass().getSimpleName() + "构造器调用"); + } + + @Override + public String toString() { + return "AMail{" + + "name='" + name + '\'' + + ", emailAddress='" + emailAddress + '\'' + + ", content='" + content + '\'' + + '}'; + } +} diff --git a/src/main/java/top/fjy8018/designpattern/pattern/creational/prototype/before/BMailUtil.java b/src/main/java/top/fjy8018/designpattern/pattern/creational/prototype/before/BMailUtil.java new file mode 100644 index 0000000..4c6740e --- /dev/null +++ b/src/main/java/top/fjy8018/designpattern/pattern/creational/prototype/before/BMailUtil.java @@ -0,0 +1,24 @@ +package top.fjy8018.designpattern.pattern.creational.prototype.before; + +import lombok.extern.slf4j.Slf4j; +import top.fjy8018.designpattern.pattern.creational.prototype.before.BMail; + +import java.text.MessageFormat; + +/** + * 邮件发送类 + * + * @author F嘉阳 + * @date 2018-09-25 20:42 + */ +@Slf4j +public class BMailUtil { + public static void sendEmail(BMail mail) { + String content = "向{0}同学,邮件地址:{1},邮件内容:{2}发送邮件成功"; + log.info(MessageFormat.format(content, mail.getName(), mail.getEmailAddress(), mail.getContent())); + } + + public static void saveOriginMail(BMail mail) { + log.info("存储Mail记录,originMailContent:{}", mail.getContent()); + } +} diff --git a/src/test/java/top/fjy8018/designpattern/pattern/creational/prototype/before/BMailTest.java b/src/test/java/top/fjy8018/designpattern/pattern/creational/prototype/before/BMailTest.java new file mode 100644 index 0000000..e7a9c28 --- /dev/null +++ b/src/test/java/top/fjy8018/designpattern/pattern/creational/prototype/before/BMailTest.java @@ -0,0 +1,71 @@ +package top.fjy8018.designpattern.pattern.creational.prototype.before; + +import lombok.extern.slf4j.Slf4j; +import org.junit.jupiter.api.AfterEach; +import org.junit.jupiter.api.BeforeEach; +import org.junit.jupiter.api.Test; +import top.fjy8018.designpattern.pattern.creational.prototype.after.AMail; +import top.fjy8018.designpattern.pattern.creational.prototype.after.AMailUtil; + +@Slf4j +class BMailTest { + + private long start; + + @BeforeEach + void init() { + start = System.currentTimeMillis(); + } + + @AfterEach + void destory() { + log.debug("耗时{}ms", System.currentTimeMillis() - start); + } + + /** + * 每次实例化对象,耗时长——耗时613ms + * + * @throws Exception + */ + @Test + void before() throws Exception { + BMail mail = new BMail(); + mail.setContent("原始正文"); + for (int i = 0; i < 5; i++) { + // 初始化临时发送邮件对象,防止原始正文被最后一个对象覆盖 + BMail tempMail = new BMail(); + tempMail.setName("学员" + i); + tempMail.setContent("正文" + i); + tempMail.setEmailAddress("地址" + i); + BMailUtil.sendEmail(tempMail); + } + // 本意希望在发送完所有邮件后保存开始的正文 + BMailUtil.saveOriginMail(mail); + + } + + /** + * 调用克隆方法(浅拷贝,因为没有对每个属性实现克隆方法),显然速度更快——耗时110ms + * + * @throws Exception + */ + @Test + void after() throws Exception { + AMail mail = new AMail(); + mail.setContent("原始正文"); + // 通过hashCode查看是否为同一个对象 + log.debug(Integer.toHexString(mail.hashCode())); + for (int i = 0; i < 5; i++) { + // 初始化临时发送邮件对象,防止原始正文被最后一个对象覆盖 + AMail tempMail = (AMail) mail.clone(); + tempMail.setName("学员" + i); + tempMail.setContent("正文" + i); + tempMail.setEmailAddress("地址" + i); + AMailUtil.sendEmail(tempMail); + log.debug(Integer.toHexString(tempMail.hashCode())); + } + // 本意希望在发送完所有邮件后保存开始的正文 + AMailUtil.saveOriginMail(mail); + + } +} \ No newline at end of file