32 设计模式:策略模式-行为型模式

153 阅读6分钟

工资不多,知之甚少。

行为型模式之:

  • 观察者模式(Observer) ✅ 重要程度:⭐️⭐️⭐️⭐️⭐️

  • 迭代器模式(Iterator) ✅ 重要程度:⭐️⭐️⭐️⭐️⭐️

  • 策略模式(Strategy) ✅ 重要程度:⭐️⭐️⭐️⭐️

  • 职责链模式(Chain of Responsibility)
    重要程度:⭐️⭐️⭐️

  • 命令模式(Command)
    重要程度:⭐️⭐️⭐️⭐️

  • 解释器模式(Interpreter)
    重要程度:⭐️

  • 中介者模式(Mediator)
    重要程度:⭐️⭐️

  • 备忘录模式(Memento)
    重要程度:⭐️⭐️

  • 状态模式(State)
    重要程度:⭐️⭐️⭐️

  • 模板方法模式(Template Method)
    重要程度:⭐️⭐️⭐️

  • 访问者模式(Visitor)
    重要程度:⭐️

1.什么是策略模式

策略设计模式是一种行为设计模式,它允许在运行时根据需要选择算法或策略。在策略模式中,可以定义一组算法,并且将每个算法封装在单独的类中,使得它们可以互相替换,而不会影响到客户端代码。

在实际的项目开发中,这个模式也比较常用。最常见的应用场景是,利用它来避免冗长的 if-else 或 switch 分支判断。

2.策略模式的使用

首先,看一个chatgpt给出的例子。

举例来说,假设有一个电商平台,针对不同的商品,可以采用不同的促销策略。在这种情况下,可以使用策略模式。具体的促销策略(如打折、满减、赠品等)被封装在各自的类中,而客户端可以根据需要选择合适的促销策略来应用于商品。

// 定义促销策略接口
interface PromotionStrategy {
    void applyPromotion();
}

// 打折策略类
class DiscountPromotion implements PromotionStrategy {
    @Override
    public void applyPromotion() {
        System.out.println("Applying discount promotion...");
    }
}

// 满减策略类
class FullReductionPromotion implements PromotionStrategy {
    @Override
    public void applyPromotion() {
        System.out.println("Applying full reduction promotion...");
    }
}

// 购物车类
class ShoppingCart {
    private PromotionStrategy promotionStrategy;

    // 设置促销策略
    public void setPromotionStrategy(PromotionStrategy promotionStrategy) {
        this.promotionStrategy = promotionStrategy;
    }

    // 应用促销策略
    public void applyPromotion() {
        if (promotionStrategy != null) {
            promotionStrategy.applyPromotion();
        }
    }
}

// 客户端代码
public class Main {
    public static void main(String[] args) {
        ShoppingCart cart = new ShoppingCart();

        // 假设购物车中有10件商品
        int itemCount = 10;
        
        // 根据不同的商品数量选择不同的促销策略
        if (itemCount > 5) {
            // 设置打折策略
            cart.setPromotionStrategy(new DiscountPromotion());
        } else {
            // 设置满减策略
            cart.setPromotionStrategy(new FullReductionPromotion());
        }

        cart.applyPromotion(); // Applying discount promotion...
    }
}

通过策略模式,客户端可以在运行时动态地选择并应用不同的促销策略,而不需要修改现有的代码逻辑。

能不能提炼一下呢?策略模式的核心点是什么呢?

1.定义过程,实现一个接口,便于扩展

// 定义促销策略接口
interface PromotionStrategy {
    void applyPromotion();
}

// 打折策略类
class DiscountPromotion implements PromotionStrategy {
    @Override
    public void applyPromotion() {
        System.out.println("Applying discount promotion...");
    }
}

// 满减策略类
class FullReductionPromotion implements PromotionStrategy {
    @Override
    public void applyPromotion() {
        System.out.println("Applying full reduction promotion...");
    }
}

1.策略过程,区分使用哪一种实现类

// 购物车类
class ShoppingCart {
    private PromotionStrategy promotionStrategy;

    // 设置促销策略
    public void setPromotionStrategy(PromotionStrategy promotionStrategy) {
        this.promotionStrategy = promotionStrategy;
    }

    // 应用促销策略
    public void applyPromotion() {
        if (promotionStrategy != null) {
            promotionStrategy.applyPromotion();
        }
    }
}

 // 根据不同的商品数量选择不同的促销策略
    if (itemCount > 5) {
        // 设置打折策略
        cart.setPromotionStrategy(new DiscountPromotion());
    } else {
        // 设置满减策略
        cart.setPromotionStrategy(new FullReductionPromotion());
    }

通俗的总结就是将复杂的if-else判断做了封装

3.策略模式的实际使用

策略模式在许多开源框架和库中都有广泛的应用。以下是一些常见的开源框架和库,它们使用了策略模式或类似的设计模式:

  1. Gson: Gson是Google提供的一个Java库,用于将Java对象转换为JSON表示形式,或者将JSON字符串转换为Java对象。在Gson中,使用了策略模式来处理不同类型的数据转换。
  2. OkHttp: OkHttp是一个流行的HTTP客户端库,用于在Android和Java应用程序中进行网络请求。它使用了拦截器模式,其中每个拦截器都是一个独立的策略,用于处理不同的HTTP请求和响应。
  3. Spring Framework: Spring框架是一个综合的Java开发框架,它提供了许多功能和组件来简化企业级应用程序的开发。Spring框架中的依赖注入和AOP(面向切面编程)功能都是基于策略模式实现的。
  4. Apache Commons Collections: Apache Commons Collections是一个Java集合框架,提供了许多实用的集合类和工具。它的Transformer接口和Closure接口是策略模式的典型应用,用于在集合上执行操作。
  5. Guava: Guava是Google提供的一个Java开发库,提供了许多实用的工具类和集合类型。在Guava中,有许多函数式接口和抽象类,它们可以被视为策略模式的具体实现。

策略模式和工厂模式的关系

  1. 策略模式(Strategy Pattern):返回算法

    • 策略模式主要关注的是定义一系列算法,并将每个算法封装成独立的策略对象,使得它们可以相互替换,而且可以独立于客户端使用。
    • 策略模式通过定义一组算法来实现业务逻辑的不同行为,客户端可以根据需要动态地选择合适的策略对象。
    • 策略模式将算法的实现和客户端解耦,提供了更灵活和可扩展的设计。
  2. 工厂模式(Factory Pattern):返回对象

    • 工厂模式旨在将对象的创建和使用分离,通过工厂来统一管理对象的创建过程,从而使客户端代码不需要直接依赖于具体的对象创建逻辑。
    • 工厂模式可以根据客户端的请求返回不同的子类实例,而客户端只需要知道接口或抽象类的名称,而不需要了解具体的实现细节。
  • 工厂模式可以用来创建不同的策略对象,而客户端可以通过工厂获取特定的策略对象,而不必知道策略对象的具体类。
  • 策略模式可以作为工厂模式中创建的具体产品的一种使用方式,以提供多样化的行为选择。

综上所述,策略模式和工厂模式在设计和用途上有所不同,但它们可以在某些情况下结合使用,以实现更灵活和可扩展的设计。

4.策略模式的优缺点

优点:

  1. 易于扩展和维护: 策略模式将每个算法封装成一个独立的类,使得新增或修改算法变得简单,不会影响其他算法的实现。
  2. 减少条件语句: 策略模式可以减少大量的条件语句,使代码更清晰、可读性更强,易于理解和维护。
  3. 提高代码复用: 策略模式将具体的算法封装在独立的类中,可以在不同的上下文中复用相同的算法。
  4. 符合开闭原则: 策略模式使得新增算法时只需添加新的策略类,而无需修改现有的代码,符合开闭原则。

缺点:

  1. 客户端需要了解不同的策略: 客户端需要了解不同的策略类及其区别,可能需要理解多个策略类的实现细节。
  2. 增加类的数量: 策略模式会导致系统中类的数量增加,每个具体策略都需要一个单独的类,使得类的数量增加,可能会增加代码的复杂性。
  3. 选择合适的策略: 如果策略类数量过多,选择合适的策略可能会增加难度。