设计模式实战:从理论到代码的优雅实践
前言
大家好。最近在代码 review 中发现很多同学对设计模式的理解停留在理论层面,没有真正应用到实际项目中。今天我想分享一下设计模式在实际项目中的应用经验,希望能帮助大家更好地理解和使用设计模式。
设计模式的本质
在开始具体的模式之前,我们需要理解设计模式的本质:
- 解决问题的模板:设计模式是解决特定问题的经验总结
- 代码复用:通过模式可以提高代码的复用性
- 可维护性:良好的设计模式可以提高代码的可维护性
- 可扩展性:设计模式可以使代码更容易扩展
常用设计模式实战
1. 单例模式(Singleton)
应用场景:需要全局唯一实例的场景,如配置管理、日志记录等
代码示例:
// 线程安全的单例模式(双重检查锁)
public class ConfigManager {
private static volatile ConfigManager instance;
private final Properties properties;
private ConfigManager() {
// 加载配置文件
properties = new Properties();
try {
properties.load(ConfigManager.class.getClassLoader().getResourceAsStream("config.properties"));
} catch (IOException e) {
// 处理异常
}
}
public static ConfigManager getInstance() {
if (instance == null) {
synchronized (ConfigManager.class) {
if (instance == null) {
instance = new ConfigManager();
}
}
}
return instance;
}
public String getProperty(String key) {
return properties.getProperty(key);
}
}
2. 工厂模式(Factory)
应用场景:需要根据不同条件创建不同对象的场景
代码示例:
// 产品接口
public interface PaymentProcessor {
void process(double amount);
}
// 具体产品
public class AlipayProcessor implements PaymentProcessor {
@Override
public void process(double amount) {
System.out.println("使用支付宝处理支付:" + amount);
}
}
public class WechatPayProcessor implements PaymentProcessor {
@Override
public void process(double amount) {
System.out.println("使用微信支付处理支付:" + amount);
}
}
// 工厂类
public class PaymentProcessorFactory {
public static PaymentProcessor createProcessor(String type) {
switch (type) {
case "alipay":
return new AlipayProcessor();
case "wechat":
return new WechatPayProcessor();
default:
throw new IllegalArgumentException("不支持的支付类型:" + type);
}
}
}
// 使用示例
public class PaymentService {
public void pay(String type, double amount) {
PaymentProcessor processor = PaymentProcessorFactory.createProcessor(type);
processor.process(amount);
}
}
3. 策略模式(Strategy)
应用场景:需要根据不同策略执行不同算法的场景
代码示例:
// 策略接口
public interface SortStrategy {
void sort(int[] array);
}
// 具体策略
public class BubbleSortStrategy implements SortStrategy {
@Override
public void sort(int[] array) {
// 冒泡排序实现
for (int i = 0; i < array.length - 1; i++) {
for (int j = 0; j < array.length - i - 1; j++) {
if (array[j] > array[j + 1]) {
int temp = array[j];
array[j] = array[j + 1];
array[j + 1] = temp;
}
}
}
}
}
public class QuickSortStrategy implements SortStrategy {
@Override
public void sort(int[] array) {
// 快速排序实现
quickSort(array, 0, array.length - 1);
}
private void quickSort(int[] array, int low, int high) {
if (low < high) {
int pivot = partition(array, low, high);
quickSort(array, low, pivot - 1);
quickSort(array, pivot + 1, high);
}
}
private int partition(int[] array, int low, int high) {
int pivot = array[high];
int i = low - 1;
for (int j = low; j < high; j++) {
if (array[j] <= pivot) {
i++;
int temp = array[i];
array[i] = array[j];
array[j] = temp;
}
}
int temp = array[i + 1];
array[i + 1] = array[high];
array[high] = temp;
return i + 1;
}
}
// 上下文类
public class Sorter {
private SortStrategy strategy;
public Sorter(SortStrategy strategy) {
this.strategy = strategy;
}
public void setStrategy(SortStrategy strategy) {
this.strategy = strategy;
}
public void sort(int[] array) {
strategy.sort(array);
}
}
// 使用示例
public class Client {
public static void main(String[] args) {
int[] array = {5, 2, 8, 1, 9};
Sorter sorter = new Sorter(new BubbleSortStrategy());
sorter.sort(array);
// 切换策略
sorter.setStrategy(new QuickSortStrategy());
sorter.sort(array);
}
}
4. 观察者模式(Observer)
应用场景:需要对象间一对多依赖的场景,如事件监听、消息通知等
代码示例:
// 主题接口
public interface Subject {
void registerObserver(Observer observer);
void removeObserver(Observer observer);
void notifyObservers();
}
// 观察者接口
public interface Observer {
void update(String message);
}
// 具体主题
public class MessageSubject implements Subject {
private List<Observer> observers = new ArrayList<>();
private String message;
@Override
public void registerObserver(Observer observer) {
observers.add(observer);
}
@Override
public void removeObserver(Observer observer) {
observers.remove(observer);
}
@Override
public void notifyObservers() {
for (Observer observer : observers) {
observer.update(message);
}
}
public void setMessage(String message) {
this.message = message;
notifyObservers();
}
}
// 具体观察者
public class EmailObserver implements Observer {
@Override
public void update(String message) {
System.out.println("邮件通知:" + message);
}
}
public class SmsObserver implements Observer {
@Override
public void update(String message) {
System.out.println("短信通知:" + message);
}
}
// 使用示例
public class Client {
public static void main(String[] args) {
MessageSubject subject = new MessageSubject();
Observer emailObserver = new EmailObserver();
Observer smsObserver = new SmsObserver();
subject.registerObserver(emailObserver);
subject.registerObserver(smsObserver);
subject.setMessage("系统更新通知");
}
}
5. 装饰器模式(Decorator)
应用场景:需要动态为对象添加功能的场景
代码示例:
// 组件接口
public interface Coffee {
String getDescription();
double getCost();
}
// 具体组件
public class Espresso implements Coffee {
@Override
public String getDescription() {
return "浓缩咖啡";
}
@Override
public double getCost() {
return 20.0;
}
}
// 装饰器抽象类
public abstract class CoffeeDecorator implements Coffee {
protected Coffee coffee;
public CoffeeDecorator(Coffee coffee) {
this.coffee = coffee;
}
@Override
public String getDescription() {
return coffee.getDescription();
}
@Override
public double getCost() {
return coffee.getCost();
}
}
// 具体装饰器
public class MilkDecorator extends CoffeeDecorator {
public MilkDecorator(Coffee coffee) {
super(coffee);
}
@Override
public String getDescription() {
return coffee.getDescription() + ", 牛奶";
}
@Override
public double getCost() {
return coffee.getCost() + 5.0;
}
}
public class SugarDecorator extends CoffeeDecorator {
public SugarDecorator(Coffee coffee) {
super(coffee);
}
@Override
public String getDescription() {
return coffee.getDescription() + ", 糖";
}
@Override
public double getCost() {
return coffee.getCost() + 2.0;
}
}
// 使用示例
public class Client {
public static void main(String[] args) {
Coffee coffee = new Espresso();
System.out.println(coffee.getDescription() + ":" + coffee.getCost());
coffee = new MilkDecorator(coffee);
System.out.println(coffee.getDescription() + ":" + coffee.getCost());
coffee = new SugarDecorator(coffee);
System.out.println(coffee.getDescription() + ":" + coffee.getCost());
}
}
设计模式的选择原则
- 问题导向:根据具体问题选择合适的设计模式
- 简单优先:不要过度设计,简单的解决方案往往更好
- 可扩展性:考虑未来的需求变化
- 代码可读性:选择易于理解的设计模式
- 性能考虑:在性能敏感的场景中选择合适的模式
实际项目中的应用建议
- 从小处开始:在小的模块中应用设计模式
- 团队共识:确保团队成员对设计模式有一致的理解
- 文档说明:为使用的设计模式添加文档说明
- 代码审查:在代码审查中关注设计模式的应用
- 持续学习:不断学习和实践新的设计模式
总结
设计模式是解决特定问题的经验总结,正确使用设计模式可以提高代码的质量和可维护性。在实际项目中,我们需要:
- 理解设计模式的本质和应用场景
- 根据具体问题选择合适的设计模式
- 灵活应用设计模式,而不是生搬硬套
- 不断学习和实践,积累经验
记住,设计模式是工具,不是目的。选择最适合当前问题的解决方案才是最重要的。
如果你有任何问题或想法,欢迎在评论区留言,我会一一回复。
1万+

被折叠的 条评论
为什么被折叠?



