适配器模式
简述解决接口不兼容问题。
话不多说,看个案例吧。
优化案例最初版v0在真实的开发场景中,系统的每个模块都是分配给不同的团队或个人来开发的。这使得事前沟通变得尤为重要,且沟通问题也时有发生。现在公司有两个模块无法兼容,难道只能重写其中的一个吗?
1234567891011121314151617181920212223242526272829303132class User { String name; String sex; int age; // 剩下的属性就不写了,都是废话没啥意义 public User(String name, String sex, int age) { this.name = name; this.sex = sex; this.age = age; }}interface Filter { List<User> findAll(); User findByName(String name);}cl ...
策略模式
简述预先定义有着不同执行过程但结果相同的算法族,运行时指定所需算法。
算法族此处为一组有共同主题的有相同结果的不同算法的集合。
话不多说,看个优化案例。
优化案例最初版v0不使用策略模式的案例。四种不同的计算策略。客户端的代码如下。
12345678910111213141516// 客户端public class Client { public static void main(String[] args) { String target = "公园"; Scanner sc = new Scanner(System.in); String input = sc.next(); if ("foot".equals(input)) { System.out.println("徒步到目的地:" + target); } else if ("bike".equals(in ...
责任链模式
简述将各个功能拆分后分别封装(各功能解耦),需要时可自由组合(包括执行顺序)
话不多说,看个优化案例吧。
优化案例最初版以下是模拟客户端想服务端发送请求的业务流程。
客户端调用代码如下。
123456789101112131415161718// 客户端public class Client { public static void main(String[] args) { Map<String, String> request = new HashMap<>(); request.put("username", "admin"); request.put("password", "admin"); service(request); } public static void service(Map<String, String> request) { ...
抽象工厂模式
简述实现对客户端中对象族的平替。
对象族具有共同主题的一组对象的集合。比如,华为的手机,笔记本,平板可以统称为华为族。
我们借以下案例来说说如何使用抽象工厂模式平替对象族。
优化案例最初版12345678910111213141516171819202122232425262728293031323334353637// 上传模块的接口public interface Uploader { void upload(String fileName);}// 下载模块的接口public interface Downloader { void download(String fileName);}// Linux环境下的上传实现public class LinuxUploader implements Uploader { public void upload(String fileName) { System.out.printf("[Linux]正在上传%s...", fi ...
组合模式
简述将对象集合组合成树形结构,使客户端可以以一致的方式处理单个对象(叶子节点)和组合对象(根节点)
话不多说,上优化案例。
优化案例最初版v0不使用组合模式。现有一个文件和目录的管理模块。如样例。
12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182838485public class File { // 文件类 private String path; private Directory parent; public File(Directory dir, String path) { if (dir == null) throw new RuntimeException("输入的dir不正确!"); if (pat ...
代理模式
简述对客户端隐藏目标类,创建代理类拓展目标类,并且对于客户端隐藏功能拓展的细节,使得客户端可以像使用目标类一样使用代理类,面向代理(客户端只与代理类交互)。
话不多说,看一个优化案例。
优化案例最初版v0目前的功能是下载可以下载文件。
12345678public BiliBiliDownloader { public byte[] download(String filePath) throws InterruptedException { System.out.printf("正在下载BiliBili文件:%s%n", filePath); // 模拟文件下载,睡个10秒 Thread.sleep(10000); return new byte[1024]; // 假装是下载文件的字节数组 }}
客户端调用代码,如下。
123456public Client { public static void main(String[] args) ...
装饰器模式
简述运行时,为原对象拓展新的行为。
相较于传统的继承来拓展新的行为,装饰器模式更为的灵活多变,当然实现起来也更为复杂。
话不多说,看个优化案例吧。
优化案例最初版v0现有系统中有设定窗口Style的模块,现在想增加一个圆角的样式。以下是现有模块的代码。
12345class Style { public void style() { System.out.println("设置Order"); }}
第一种传统的修改方式。
123456class Style { public void style() { System.out.println("设置Order"); System.out.println("设置Radius"); }}
虽然代码简单,但细想一下,如果我们日后仍然需要单独设置Order的样式怎么办。现在的代码实现已经无法满足了不是?
为此,我们可能会想到另一种方案。使用 ...
享元模式
简述
类型:结构型
目的:降低对象创建时大量属性也随之被新建而带来的性能上的消耗
话不多说,我们看一个案例。
优化案例最初版v0现在需要采购一批办公用的电脑,以下是Computer类的定义。
123456789101112131415161718192021222324252627public class Computer { private String sn; // 序列号,电脑的唯一识别码 private String brand; // 品牌 private String title; // 一个系列的名称,如Lenovo的Thinkpad private String cpu; private String memory; private String disk; private String gpu; private String keyboard; private String display; public Computer(String sn, String brand, ...
桥接模式
简述通过抽离出多个维度相互组合(聚合)来代替继承,简化系统。
话不多说,看个优化案例。
优化案例现有系统中,对于画面窗口的边框有一套样式来控制是否有圆角。因为新的需求,需要增加两套样式,一套控制边框线条的颜色(红、黄、蓝),一套控制边框有无阴影。我们来看看几种实现方式。
最初版v0我们看看用继承或实现的方式,会是什么样子。
1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192939495969798991001011021031041051061071081091101111121131141151161171181191201211221231241251261271281291301311321331341351361371381391401411421431441451461471481 ...
单例模式
简述杜绝相同对象的反复创建,提升系统性能。
话不多说,直接看实现方案例。
实现案例饿汉式项目启动时加载
123456public class Test { private static Test ins = new Test(); public static Test instance() { return ins; }}
在项目启动时就被加载 → 项目启动变慢如果对象不经常使用的话还存在浪费资源的问题。
懒汉式懒加载,在使用时才被加载
12345678public class Test { private static Test ins; public static synchronized Test instance() { if (ins == null) ins = new Test(); return ins; }}
在项目启动时并不加载 → 项目加载变快第一次使用时加载 → 存在第一次使用时等待过长的问题使用synch ...