Java设计模式之java策略模式详解

Java设计模式之Java策略模式详解

什么是Java策略模式?

Java策略模式是一种行为型设计模式,它定义了算法族,即一组具有相同目的和不同实现的算法,让它们之间可以相互替换。这个模式让算法的变化独立于使用算法的客户端,从而实现算法行为的变化而无需更改使用算法的客户端。

Java策略模式的三个角色

Java策略模式一般涉及到如下三个角色:

  1. Context 上下文对象:持有一个Strategy对象,并在其内部的某个方法中调用该对象的方法实现具体的算法行为。
  2. Strategy 策略接口:封装具体的算法实现,提供一个执行算法的方法进行调用。
  3. Concrete Strategy 具体策略:实现策略接口,定义具体的算法实现方法。

Java策略模式的优点

  1. 策略模式可避免使用多重条件语句(if...else语句)。
  2. 策略模式为算法实现提供了更具优化的更换方案,增强系统的灵活性和维护性。
  3. 策略模式将一系列的算法封装成类独立于客户端进行独立修改和扩展。

Java策略模式的示例

下面举两个简单的Java策略模式的示例:

示例一:鸭子游戏

假设我们有一个鸭子游戏,游戏里有多种不同类型的鸭子,它们需要实现三个行为:游泳、飞行和叫声。

// 鸭子抽象类
public abstract class Duck {
    SwimBehavior swimBehavior;
    FlyBehavior flyBehavior;
    QuackBehavior quackBehavior;

    public void setSwimBehavior(SwimBehavior sb) {
        swimBehavior = sb;
    }

    public void setFlyBehavior(FlyBehavior fb) {
        flyBehavior = fb;
    }

    public void setQuackBehavior(QuackBehavior qb) {
        quackBehavior = qb;
    }

    public void swim() {
        swimBehavior.swim();
    }

    public void fly() {
        flyBehavior.fly();
    }

    public void quack() {
        quackBehavior.quack();
    }

    public abstract void display();
}

// 游泳行为接口
public interface SwimBehavior {
    void swim();
}

// 飞行行为接口
public interface FlyBehavior {
    void fly();
}

// 叫声行为接口
public interface QuackBehavior {
    void quack();
}

具体的鸭子类型分别实现抽象类Duck,并设置各自的游泳、飞行和叫声行为:

// 绿头鸭
public class MallarDuck extends Duck {
    public MallarDuck() {
        swimBehavior = new SwimWithSLippers();
        flyBehavior = new FlyWithWings();
        quackBehavior = new Quack();
    }

    @Override
    public void display() {
        System.out.println("MallarDuck");
    }
}

// 红头鸭
public class RedheadDuck extends Duck {
    public RedheadDuck() {
        swimBehavior = new SwimWithOutSLippers();
        flyBehavior = new FlyWithWings();
        quackBehavior = new Quack();
    }

    @Override
    public void display() {
        System.out.println("RedheadDuck");
    }
}

// 橡皮鸭
public class RubberDuck extends Duck {
    public RubberDuck() {
        swimBehavior = new SwimWithOutSLippers();
        flyBehavior = new NoFly();
        quackBehavior = new Squeak();
    }

    @Override
    public void display() {
        System.out.println("RubberDuck");
    }
}

// 诱饵鸭
public class DecoyDuck extends Duck {
    public DecoyDuck() {
        swimBehavior = new SwimWithOutSLippers();
        flyBehavior = new NoFly();
        quackBehavior = new MuteQuack();
    }

    @Override
    public void display() {
        System.out.println("DecoyDuck");
    }
}

游戏中不同的鸭子类型,根据其具体的行为进行配置:

public class DuckGame {
    public static void main(String[] args) {
        Duck mallarDuck = new MallarDuck();
        mallarDuck.swim();
        mallarDuck.fly();
        mallarDuck.quack();

        Duck rubberDuck = new RubberDuck();
        rubberDuck.swim();
        rubberDuck.fly();   // 诱饵鸭和橡皮鸭不能飞行,因此具体的策略实现为NoFly;
        rubberDuck.quack();
    }
}

在上述示例中,游戏中不同的鸭子类型根据具体的行为进行配置,并能够根据需要动态的配置每个鸭子的具体实现。

示例二:商城商品打折

假设我们有一个商城系统,对于不同价格区间的商品,需要根据具体的折扣策略进行优惠。

// 商品抽象类
public abstract class Goods {
    // 获取商品的价格
    public abstract double getPrice();

    // 获取打折后的价格
    public abstract double getDiscountPrice(DiscountStrategy discountStrategy);
}

// 折扣策略接口
public interface DiscountStrategy {
    double discount(double price);
}

// 新手客户策略
public class NewCustomerDiscount implements DiscountStrategy {
    @Override
    public double discount(double price) {
        System.out.println("新手客户打9折!");
        return price * 0.9;
    }
}

// 老客户策略
public class OldCustomerDiscount implements DiscountStrategy {
    @Override
    public double discount(double price) {
        System.out.println("老客户打8折!");
        return price * 0.8;
    }
}

// VIP客户策略
public class VIPCustomerDiscount implements DiscountStrategy {
    @Override
    public double discount(double price) {
        System.out.println("VIP客户打7折!");
        return price * 0.7;
    }
}

// 具体的商品实现类
public class GoodsImpl extends Goods {
    private double price;

    public GoodsImpl(double price) {
        this.price = price;
    }

    @Override
    public double getPrice() {
        return price;
    }

    @Override
    public double getDiscountPrice(DiscountStrategy discountStrategy) {
        return discountStrategy.discount(price);
    }
}

不同价格区间的商品根据打折策略进行打折,商城系统实现如下:

public class DiscountGame {
    public static void main(String[] args) {
        Goods goods1 = new GoodsImpl(100.0);
        double discountPrice1 = goods1.getDiscountPrice(new NewCustomerDiscount());
        System.out.println("物品1的打折后价格:" + discountPrice1);

        Goods goods2 = new GoodsImpl(500.0);
        double discountPrice2 = goods2.getDiscountPrice(new OldCustomerDiscount());
        System.out.println("物品2的打折后价格:" + discountPrice2);

        Goods goods3 = new GoodsImpl(1000.0);
        double discountPrice3 = goods3.getDiscountPrice(new VIPCustomerDiscount());
        System.out.println("物品3的打折后价格:" + discountPrice3);
    }
}

在上述示例中,不同价格区间的商品根据打折策略进行打折,商城系统具有完善的策略规定,并能够根据需要动态的配置不同的打折策略。

阅读剩余 80%

本站文章如无特殊说明,均为本站原创,如若转载,请注明出处:Java设计模式之java策略模式详解 - Python技术站

(0)
上一篇 2023年5月19日
下一篇 2023年5月19日

相关文章

  • jsp搜索引擎

    JSP(Java Server Pages)搜索引擎需要基于Java编程语言进行开发,可以使用已有的开源框架、工具库进行快速开发。 以下是JSP搜索引擎的完整攻略: 步骤一:创建Web应用程序 使用任意一种Java Web框架创建一个全新的Web应用程序。(注意:在接下来的步骤中,以SpringMVC框架为例进行讲解) 步骤二:集成Lucene搜索引擎 Lu…

    Java 2023年6月15日
    00
  • SpringCloud Feign使用ApacheHttpClient代替默认client方式

    SpringCloud Feign使用ApacheHttpClient代替默认client方式 在SpringCloud中,Feign默认使用URLConnection作为HTTP客户端发送请求。但是,我们可以通过修改配置,使用基于Apache HttpClient的方式发送HTTP请求代替默认的URLConnection。这样可以获得更好的性能和可配置性。…

    Java 2023年6月2日
    00
  • java使用jdbc连接数据库工具类和jdbc连接mysql数据示例

    使用Java连接数据库一般都会使用Java Database Connectivity(JDBC)技术。JDBC 是一种Java提供的标准化的数据库操作接口,支持多种数据库,包括MySQL、Oracle、SQL Server等等。在Java中,使用JDBC编写程序连接数据库是比较常见的,接下来详细讲解一下如何使用 JDBC 连接 MySQL 数据库及其工具类…

    Java 2023年5月19日
    00
  • 详解Java事件编程的使用

    详解Java事件编程的使用 什么是Java事件编程? 在Java编程中,事件是指程序或用户可以监测到并有可能做出反应的操作或通知。Java事件编程是基于事件模型的一种编程方法,也是一种事件驱动的编程方式。 事件驱动编程的核心在于将程序设计为一个能够响应特定事件的系统。在这种模式下,程序设计者无需关注具体的事件何时发生,只需要定义如何响应事件即可。 Java事…

    Java 2023年5月23日
    00
  • Spring Boot应用程序中如何使用Keycloak详解

    Spring Boot应用程序中如何使用Keycloak详解 Keycloak是一个强大的、开源、易于使用的认证和授权管理解决方案。Spring Boot提供了与Keycloak的集成,可以轻松地保护和管理您的应用程序。 本文将介绍如何在Spring Boot应用程序中快速集成Keycloak,以便您的Web应用程序能够以安全的方式使用它。 准备工作 在开始…

    Java 2023年5月20日
    00
  • Java调用dll文件的实现解析

    下面就来详细讲解“Java调用dll文件的实现解析”的完整攻略。 什么是DLL文件 首先,我们需要了解一下DLL文件,DLL是Dynamic Link Library的缩写,是动态链接库的意思,它是Windows系统中用来提供一些功能的动态库文件,以实现代码复用,减少内存占用等等的目的。 在Windows系统中,有许多功能模块通过DLL文件的方式进行提供,例…

    Java 2023年5月19日
    00
  • javaweb页面附件、图片下载及打开(实现方法)

    下面是详细讲解“javaweb页面附件、图片下载及打开(实现方法)”的完整攻略: 1. 附件下载 实现方法 创建一个下载链接或按钮,设置其href属性为要下载的文件资源的url地址,如下所示: <a href="/attachments/file.pdf">下载</a> 在后端处理器中,根据url地址获取文件资源,…

    Java 2023年6月15日
    00
  • 使用cmd根据WSDL网址生成java客户端代码的实现

    使用cmd根据WSDL网址生成java客户端代码的实现,可以分为以下几个步骤: 打开cmd窗口 进入java/bin目录 敲入以下命令,其中”your_web_service_url”为你需要生成代码的WSDL服务的地址,”your_package_name”为你生成的Java代码所在的包名。 wsimport -keep -verbose your_web…

    Java 2023年5月19日
    00
合作推广
合作推广
分享本页
返回顶部