一、前言

策略模式可能是在工作中使用最多的,也是在面试中最常提到的,代码重构和优化的必备!

小编之前也是一直说,其实没有真正的实战;最近有了机会实战了一下,来分享一下使用心得和在企业级的使用!

二、策略模式

1. 什么是策略模式

策略模式,英文全称是 Strategy Design Pattern。在 GoF 的《设计模式》一书中,它是这样定义的:

定义一族算法类,将每个算法分别封装起来,让它们可以互相替换。策略模式可以使算法的变化独立于使用它们的客户端(这里的客户端代指使用算法的代码)。

2. 策略模式结构组成

  • Strategy:抽象策略类,一般为接口或者策略类
  • ConcreteStrategy:具体算法实现策略类
  • Context:环境或者上下文类,用于统一执行具体策略

其实以上三部分用白话文来解释就是:

需要一个接口和策略进行规范和约束接口和方法,这时需要一些具体的实现算法类去继承或者实现刚刚的接口和策略,最后通过一个环境或者上下文,也可以叫做工厂根据类型进行调用具体的算法!

3. 使用场景

  • 避免冗长的 if-else 或 switch 分支判断
  • 需要动态地在几种算法中选择一种
  • 对客户隐藏具体策略 (算法) 的实现细节,彼此完全独立,扩展其余不受影响

具体场景一般为:

  • 支付方式选择
  • 打折、满减方式选择
  • 根据类型调用不同的系统

4. 优缺点

优点:

  • 扩展性好
  • 符合开闭原则
  • 符合单一职责原则
  • 可读性好
  • 便于维护
  • 避免多层判断

缺点:

  • 策略过多,导致策略类
  • 对新手读代码不友好

三、策略模式实战

1. 实战例子

今天小编根据春夏秋冬四季需要做不同的事情来演示一下策略模式的使用方案;

需求是:

如果是春天,就要去放风筝

如果是夏天,就要去游泳

如果是秋天,就要去看枫叶

如果是冬天,就要去打雪仗

没有使用策略模式的话,肯定就是

if-if else进行实现!

下面就带大家体会一下具体使用哈!!

2. 策略接口

/**
* 四季策略
* @author wangzhenjun
* @date 2022/12/1 9:30
*/
public interface SeasonsStrategy { /**
* 根据季节去执行不同的方案
* @param seasons
* @return
*/
String execute(String seasons);
}

3. 春季具体实现

/**
* 春季具体实现
* @author wangzhenjun
* @date 2022/12/1 9:34
*/
// 指定容器的名称,不指定默认为类名称首字母小写
@Component("spring")
public class SpringStrategy implements SeasonsStrategy{
@Override
public String execute(String seasons) { return seasons + "来了!我们一起去放风筝吧!";
}
}

4. 夏季具体实现

/**
* 夏季具体实现
* @author wangzhenjun
* @date 2022/12/1 9:34
*/
// 指定容器的名称,不指定默认为类名称首字母小写
@Component("summer")
public class SummerStrategy implements SeasonsStrategy{
@Override
public String execute(String seasons) { return seasons + "来了!我们一起去游泳吧!";
}
}

5. 秋季具体实现

/**
* 秋季具体实现
* @author wangzhenjun
* @date 2022/12/1 9:34
*/
// 指定容器的名称,不指定默认为类名称首字母小写
@Component("autumn")
public class AutumnStrategy implements SeasonsStrategy{
@Override
public String execute(String seasons) { return seasons + "来了!我们一起去放看枫叶吧!";
}
}

6. 冬季具体实现

/**
* 冬季具体实现
* @author wangzhenjun
* @date 2022/12/1 9:34
*/
// 指定容器的名称,不指定默认为类名称首字母小写
@Component("winter")
public class WinterStrategy implements SeasonsStrategy{
@Override
public String execute(String seasons) { return seasons + "来了!我们一起去打雪仗吧!";
}
}

7. 上下文工厂实现

private Map<String, SeasonsStrategy> seasonsMap;这是最重要的,很多时候我们都知道怎么进行策略和实现怎么写,不知道怎么统一去放进去,来进行调用,可以自己放在map中。当然spring已经给我们组装好了,只要按需调用即可!

核心:

Spring会自动将Strategy接口的实现类注入到这个Map中,key为bean id,value值则为对应的策略实现类!

/**
* 环境或者上下文类,用于统一执行具体策略
* @author wangzhenjun
* @date 2022/12/1 9:56
*/
@Component
public class SeasonsFactory {
/**
* Spring会自动将Strategy接口的实现类注入到这个Map中,key为bean id,value值则为对应的策略实现类
*/
@Autowired
private Map<String, SeasonsStrategy> seasonsMap; /**
* 处理四季统一入口方法
* @param seasons
* @param beanName
* @return
*/
public String handle(String seasons,String beanName){
// 根据bean的名称获取对应的算法处理类
SeasonsStrategy seasonsStrategy = seasonsMap.get(beanName);
String execute = seasonsStrategy.execute(seasons);
return execute;
}
}

8. controller处理

@Slf4j
@RestController
@RequestMapping("/test")
public class TestController { @Autowired
private SeasonsFactory seasonsFactory; @GetMapping("/strategyTest/{seasons}/{beanName}")
public Result strategyTest(@PathVariable("seasons") String seasons,@PathVariable("beanName") String beanName){
String handle = seasonsFactory.handle(seasons, beanName);
return Result.success(handle);
}
}

9. 测试

http://localhost:8087/test/strategyTest/春天/spring



http://localhost:8087/test/strategyTest/夏天/summer

四、总结

在策略模式中定义了一系列算法,将每一个算法封装起来,并让它们可以相互替换,互不影响。

策略模式得益于按照开闭原则进行设计,各个具体算法按照单一职责原则设计; 提高了代码的复用性,对客户隐藏具体策略 (算法) 的实现细节,彼此完全独立,扩展其余不受影响;避免if-else 或 switch 分支语句判断;其缺点在于客户端必须知道所有的策略类,增加了系统中类的个数。

在日常开发一般用于消除多重判断,有时候不要为了用设计模式而用设计模式,一定要结合业务场景,过度设计也是很致命的!!

如果对你有帮助,还请不要吝啬您的发财小手,你的一键三连是我写作的动力,谢谢大家哈!!


可以看下小编的微信公众号,文章首发看,欢迎关注,一起交流哈!!

Springboot整合策略模式概念->使用场景->优缺点->企业级实战的更多相关文章

  1. springBoot整合spring security+JWT实现单点登录与权限管理--筑基中期

    写在前面 在前一篇文章当中,我们介绍了springBoot整合spring security单体应用版,在这篇文章当中,我将介绍springBoot整合spring secury+JWT实现单点登录与 ...

  2. 功能:SpringBoot整合rabbitmq,长篇幅超详细

    SpringBoot整合rabbitMq 一.介绍 消息队列(Message Queue)简称mq,本文将介绍SpringBoot整合rabbitmq的功能使用 队列是一种数据结构,就像排队一样,遵循 ...

  3. SpringBoot整合SpringSecurity示例实现前后分离权限注解

    SpringBoot 整合SpringSecurity示例实现前后分离权限注解+JWT登录认证 作者:Sans_ juejin.im/post/5da82f066fb9a04e2a73daec 一.说 ...

  4. SpringBoot整合MyBatisPlus配置动态数据源

    目录 SpringBoot整合MyBatisPlus配置动态数据源 SpringBoot整合MyBatisPlus配置动态数据源 推文:2018开源中国最受欢迎的中国软件MyBatis-Plus My ...

  5. SpringBoot整合Swagger和Actuator

    前言 本篇文章主要介绍的是SpringBoot整合Swagger(API文档生成框架)和SpringBoot整合Actuator(项目监控)使用教程. SpringBoot整合Swagger 说明:如 ...

  6. springboot整合websocket高级版

    目录 sockjs介绍 产生的原因 环境搭建 springboot整合sockjs 使用场景 聊天室开发 点对点通信 群聊 效果 总结 加入战队 微信公众号 上一章节我们说了websocket的优缺点 ...

  7. springboot整合Shiro功能案例

    Shiro 核心功能案例讲解 基于SpringBoot 有源码 从实战中学习Shiro的用法.本章使用SpringBoot快速搭建项目.整合SiteMesh框架布局页面.整合Shiro框架实现用身份认 ...

  8. SpringBoot整合Swagger2(Demo示例)

    写在前面 由于公司项目采用前后端分离,维护接口文档基本上是必不可少的工作.一个理想的状态是设计好后,接口文档发给前端和后端,大伙按照既定的规则各自开发,开发好了对接上了就可以上线了.当然这是一种非常理 ...

  9. 001 SringBoot基础知识及SpringBoot整合Mybatis

    1.原有Spring优缺点分析 (1)优点 Spring是Java企业版(Java Enterprise Edition,JEE,也称J2EE)的轻量级代替品.无需开发重量级的Enterprise J ...

  10. Redis-基本概念、java操作redis、springboot整合redis,分布式缓存,分布式session管理等

    NoSQL的引言 Redis数据库相关指令 Redis持久化相关机制 SpringBoot操作Redis Redis分布式缓存实现 Resis中主从复制架构和哨兵机制 Redis集群搭建 Redis实 ...

随机推荐

  1. 方法的重载(overload)

    1.定义:在同一个类中,允许存在一个以上的同名方法,只要它们的参数个数或者参数类型不同即可. "两同一不同":同一个类.相同方法名 参数列表不同:参数个数不同,参数类型不同 2.举 ...

  2. 20220728 - DP训练 #1

    20220728 - DP训练 #1 时间记录 \(8:00-9:00\) T1 尝试做 \(T1\),可惜并未做出,没有想到是资源分配 设置三维状态,初值一直不知道怎么设置 并且对于距离有一部分不会 ...

  3. C语言------数据类型与输入输出

    仅供借鉴.仅供借鉴.仅供借鉴(整理了一下大一C语言每个章节的练习题.没得题目.只有程序了) 文章目录 1 .实训名称 2 .实训目的及要求 3 .源代码及运行截图 4 .小结 1 .实训名称 实训2: ...

  4. 洛P8109题解

    摘自本人洛谷博客,原文章地址:https://www.luogu.com.cn/blog/cjtb666anran/solution-p8109 本题原题目摘录: 本场比赛共有 \(n\) 道题,Ci ...

  5. 利用xtrabackup8完全,增量备份及还原MySQL8

    利用xtrabackup8完全,增量备份及还原MySQL8 1.环境准备 服务器 作用 数据库版本 xtrabackup版本 10.0.0.8 数据备份 mysql8.0.26 8.0.28 10.0 ...

  6. 记录redis集群连接超时问题及解决方案

    下午同事反馈,某业务场景性能测试过程中,出现异常,提供日志报: Redis command timed out 1. 先看下日志 org.springframework.dao.QueryTimeou ...

  7. 【ASP.NET Core】MVC控制器的各种自定义:应用程序约定的接口与模型

    从本篇起,老周会连发N篇水文,总结一下在 MVC 项目中控制器的各种自定义配置. 本文内容相对轻松,重点讨论一下 MVC 项目中的各种约定接口.毕竟你要对控制器做各种自定义时,多数情况会涉及到约定接口 ...

  8. 干货,深入剖析ReentrantLock源码,推荐收藏

    ReentrantLock和Synchronized都是Java开发中最常用的锁,与Synchronized这种JVM内置锁不同的是,ReentrantLock提供了更丰富的语义.可以创建公平锁或非公 ...

  9. ironic组件硬件自检服务——ironic-inspector

    介绍 ironic-inspector是一个用于硬件自检的辅助型服务,它可以对被ironic组件管理的裸金属节点进行硬件自检,通过在裸金属节点上运行内存系统,发现裸金属节点的硬件信息,例如CPU数量和 ...

  10. Kubernetes核心技术-Controller

    Kubernetes核心技术-Controller 内容 什么是Controller Pod和Controller的关系 Deployment控制器应用场景Deployment控制器应用 yaml文件 ...