一:概述

设计模式是软件开发中解决特定问题的优秀实践方案。作为Java开发者,我们每天都在使用的JDK中其实大量运用了各种设计模式。理解这些模式在JDK中的实现,不仅能帮助我们更好地使用JDK,也能提升我们的设计能力。本文将深入探讨JDK中常见的设计模式实现。

二:具体说明

一、创建型模式

1. 单例模式(Singleton)

JDK中最典型的单例模式实现是Runtime类:

public class Runtime {private static Runtime currentRuntime = new Runtime();public static Runtime getRuntime() {return currentRuntime;}private Runtime() {}// 其他方法...
}

这个实现展示了经典的单例模式特点:

  • 私有构造方法防止外部实例化
  • 静态变量持有唯一实例
  • 静态方法提供全局访问点

2. 工厂模式(Factory)

java.util.Collections类中的静态方法提供了许多工厂方法:

List<String> synchronizedList = Collections.synchronizedList(new ArrayList<>());
Set<String> unmodifiableSet = Collections.unmodifiableSet(new HashSet<>());

`这些方法隐藏了具体实现类的细节,提供了创建特定功能集合的统一接口。

3. 建造者模式(Builder)

java.lang.StringBuilderjava.lang.StringBuffer是建造者模式的典型应用:

StringBuilder builder = new StringBuilder();
String result = builder.append("Hello").append(" ").append("World").toString();

虽然它们主要用于字符串拼接,但体现了建造者模式的核心思想:分步构建复杂对象。

二、结构型模式

1. 适配器模式(Adapter)

java.util.Arrays#asList()方法将数组适配为List:

List<String> list = Arrays.asList("a", "b", "c");

这里Arrays.asList()充当了适配器,将数组接口适配为List接口。

2. 装饰器模式(Decorator)

Java I/O流大量使用了装饰器模式:

InputStream is = new FileInputStream("test.txt");
InputStream bufferedIs = new BufferedInputStream(is);
InputStream gzipIs = new GZIPInputStream(bufferedIs);

每个装饰类都扩展了基础流的功能,而不改变其接口,这是装饰器模式的典型特征。

3. 代理模式(Proxy)

java.lang.reflect.Proxy提供了动态代理的实现:

InvocationHandler handler = new MyInvocationHandler();
MyInterface proxy = (MyInterface) Proxy.newProxyInstance(MyInterface.class.getClassLoader(),new Class[] { MyInterface.class },handler);

动态代理在AOP、RPC等场景中广泛应用。

三、行为型模式

1. 迭代器模式(Iterator)

Java集合框架中的Iterator是迭代器模式的典范:

List<String> list = Arrays.asList("a", "b", "c");
Iterator<String> it = list.iterator();
while(it.hasNext()) {System.out.println(it.next());
}

迭代器将集合的遍历操作与集合实现分离。

2. 观察者模式(Observer)

早期JDK中的java.util.Observablejava.util.Observer(Java 9已废弃)实现了观察者模式:

Observable observable = new Observable();
observable.addObserver((o, arg) -> System.out.println("Changed: " + arg));
observable.notifyObservers("Hello");

现代Java更常用PropertyChangeListener或其他事件机制。

3. 策略模式(Strategy)

java.util.Comparator是策略模式的典型例子:

Collections.sort(list, new Comparator<String>() {public int compare(String a, String b) {return b.compareTo(a);}
});

通过不同的Comparator实现,可以灵活改变排序策略。

4. 模板方法模式(Template Method)

java.io.InputStream中的read()方法:

public abstract class InputStream {public abstract int read() throws IOException;public int read(byte b[]) throws IOException {// 模板方法实现...}
}

子类只需实现抽象read()方法,非抽象方法提供了模板实现。

四、并发模式

1. 不可变对象模式(Immutable Object)

java.lang.String是最著名的不可变对象:

String s = "hello";
String s2 = s.toUpperCase(); // 返回新对象,不改变原对象

不可变对象在多线程环境下具有天然的线程安全性。

2. 线程局部存储模式(Thread Local Storage)

java.lang.ThreadLocal实现了线程局部变量:

ThreadLocal<Integer> threadLocal = ThreadLocal.withInitial(() -> 0);

每个线程访问自己的变量副本,避免了线程安全问题。

五、函数式编程模式

Java 8引入的Lambda和Stream API带来了新的模式:

1. 函数接口(Functional Interface)

java.util.function包中的各种函数式接口:

Function<String, Integer> lengthFunc = String::length;
Predicate<String> isEmpty = String::isEmpty;

这些接口支持了Java的函数式编程能力。

2. 流式处理(Fluent Interface)

Stream API的链式调用:

List<String> result = list.stream().filter(s -> s.startsWith("A")).map(String::toUpperCase).collect(Collectors.toList());

这种流畅的接口设计提高了代码的可读性。

总结

JDK中设计模式的应用无处不在,理解这些模式在核心库中的实现,可以帮助我们:

  1. 更深入地理解JDK的设计思想
  2. 在自己的代码中更好地应用这些模式
  3. 编写出更优雅、更易维护的代码

设计模式不是银弹,但它们是经过验证的解决方案。JDK中的这些实现展示了如何在实际项目中恰当地应用设计模式,值得我们反复学习和思考。

作为Java开发者,我们不仅应该了解这些模式,更应该理解它们解决的问题和适用场景,这样才能在适当的时候选择合适的设计方案。