热门标签 | HotTags
当前位置:  开发笔记 > 编程语言 > 正文

设计模式之行为型设计模式

文章目录委派模式(DelegatePattern)委派模式模拟任务分配委派模式在JDK中的应用委派模式在Spring中的应用模板方法(TemplateMethodPattern)模




文章目录


  • 委派模式(Delegate Pattern)
    • 委派模式模拟任务分配
    • 委派模式在JDK中的应用
    • 委派模式在Spring中的应用

  • 模板方法(Template Method Pattern)
    • 模板方法模拟上班
    • 模板方法在 Spring 中的应用

  • 策略模式(Strategy Pattern)
    • 策略模式实现购买商品使用不同的支付方式
    • 策略模式在JDK中的应用
    • 策略模式在Spring中的应用

  • 责任链模式
    • 责任链模式实现登录校验
    • 责任链模式在Spring中的应用

  • 迭代器模式



行为型设计模式:关注对象之间的通信。


委派模式(Delegate Pattern)

老板给项目经理下达一个任务,项目经理会根据情况分配不同的工作任务给每个员工,员工完成之后,项目经理再向老板汇报工作进度和任务。
如果要办一件事,不必自己处理,可以写一个授权委托书,授权他人代办事务。上面老板让项目经理完成一个任务,项目经理让下面的员工来办理。

应用场景:


  1. 表现层和业务层解耦合
  2. 协调多个服务之间的调用
  3. 封装一层服务查找和调用

委派模式模拟任务分配

老板下达一个任务给项目经理,项目经理拆分不同任务给不同的员工,共同完成这个任务。

抽象出员工接口,并实现不同的员工。

public interface IEmployee {
void doing(String task);
}
public class EmployeeA implements IEmployee {
@Override
public void doing(String task) {
System.out.println("我是开发人员,开始做" + task + "工作");
}
}
public class EmployeeB implements IEmployee {
@Override
public void doing(String task) {
System.out.println("我是设计人员,开始做" + task + "工作");
}
}
public class Leader implements IEmployee {
private IEmployee employeeA = new EmployeeA();
private IEmployee employeeB = new EmployeeB();
// 项目经理就是拆分任务给不同的员工来完成
@Override
public void doing(String task) {
String[] taskSplit = task.split(",");
employeeA.doing(taskSplit[0]);
employeeA.doing(taskSplit[1]);
}
}

老板下达任务给项目经理。

public class Boss {
private Leader leader = new Leader();
public void command(String task){
leader.doing(task);
}
}
public class Test {
public static void main(String[] args) {
Boss boss = new Boss();
boss.command("开发,设计");
}
}

运行结果:

我是开发人员,开始做开发工作
我是开发人员,开始做设计工作

委派模式在JDK中的应用

JVM 在加载类时使用了双亲委派机制。
一个加载器在加载类时,先把这个类委托给父类加载器去执行,如果父类加载器执行成功返回,如果父类加载器无法加载,则子加载器会自己去执行加载。


委派模式在Spring中的应用

DispatcherServlet 使用了委派模式。

比如有三个业务类:MemberController、OrderController、ProductController。

所有请求都经过 DispatchServlet 进行转发。
DispatcherServlet 会根据请求 url 来获取相应的业务类后,再调用。


模板方法(Template Method Pattern)

完成一个任务有固定的流程,抽象出固定流程的步骤,具体步骤让子类去具体实现完成。


模板方法模拟上班

公司的上班情况,简单描述一下:公司有开发、测试、HR、项目经理等人,下面使用模版方法模式,记录下所有人员的上班情况。

抽象出工作。

public abstract class Worker {
// 都是先进公司,然后工作,最后离开公司
public final void doing() {
enterCompany();
work();
exitCompany();
}
// 工作任务是不同的,让子类去实现
public abstract void work();
public void enterCompany() {
System.out.println("进入公司");
}
// 离开公司
public void exitCompany() {
System.out.println("离开公司");
}
}
public class HRWorker extends Worker{
@Override
public void work() {
System.out.println("看简历");
}
}
public class ITWorker extends Worker {
@Override
public void work() {
System.out.println("写代码");
}
}
public class Test {
public static void main(String[] args) {
Worker itWorker = new ITWorker();
itWorker.doing();
Worker hrWorker = new HRWorker();
hrWorker.doing();
}
}

运行结果:

进入公司
写代码
离开公司
进入公司
看简历
离开公司

模板方法在 Spring 中的应用

RestTemplate
JDBCTemplate


策略模式(Strategy Pattern)

将不同算法封装成一个类,每个算法完成的是同类型的问题。


策略模式实现购买商品使用不同的支付方式


策略模式在JDK中的应用

比较器是一个典型的策略模式,定义一个比较器接口,对象要排序可以实现自己的比较器实现类。

public interface Comparator {
int compare(T o1, T o2);
}

策略模式在Spring中的应用


责任链模式

各个部门协同合作完成一个任务,每个部门都有各自的职责,一个部门完成后,变回转交给下一个部门,直到所有部门都处理了,这个任务才完成。
将请求与处理解耦。
处理者只需要关注自己感兴趣的请求进行处理,对于不感兴趣的请求,直接转发给下一个节点对象。


责任链模式实现登录校验

1、校验用户名或密码是否为空。
2、校验用户名是否存在。
3、校验是否有权限。

@Data
public class Member {
private String loginName;
private String loginPass;
private String roleName;
public Member(String loginName, String loginPass) {
this.loginName = loginName;
this.loginPass = loginPass;
}
}

传统编码,在同一个方法里一个一个进行判断。

public class MemberService {
public void login(String loginName, String loginPass) {
if (StringUtils.isEmpty(loginName) || StringUtils.isEmpty(loginPass)) {
System.out.println("用户名或密码不为空,校验失败");
return;
}
System.out.println("用户名、密码校验成功");
if (!"James".equals(loginName)) {
System.out.println("用户不存在");
return;
}
Member member = new Member();
member.setRoleName("管理员");
if (!"管理员".equals(member.getRoleName())) {
System.out.println("您不是管理员,没有权限");
return;
}
System.out.println("登录成功");
}
public static void main(String[] args) {
MemberService memberService = new MemberService();
memberService.login("Ja1mes", "null");
}
}

使用责任链和建造者结合模式,将每个步骤处理连起来。
抽象出处理类。

public abstract class Handler {
// 指向下一个处理类
protected Handler chain;
// 设置下一个处理类
public void next(Handler handler) {
this.chain = handler;
}
// 具体处理逻辑
public abstract void doHandler(Member member);
// 构建一条链式处理逻辑
public static class Builder {
// 第一个处理类
private Handler head;
// 最后一个处理类
private Handler tail;
// 从头开始添加处理类
public Builder addHandler(Handler handler) {
if (this.head == null) {
// 只有一个处理类,所以不需要设置下一个处理类
this.head = this.tail = handler;
return this;
}
// 设置下一个处理类
this.tail.next(handler);
// 尾部设置为下一个处理类的引用
this.tail = handler;
return this;
}
// 返回的是第一个处理类
public Handler builder() {
return this.head;
}
}
}

具体实现三个处理类,来进行分别校验

public class ValidateHandler extends Handler {
@Override
public void doHandler(Member member) {
if (StringUtils.isEmpty(member.getLoginName()) || StringUtils.isEmpty(member.getLoginPass())) {
System.out.println("用户名或密码不为空,校验失败");
return;
}
System.out.println("用户名、密码校验成功");
chain.doHandler(member);
}
}
public class LoginHandler extends Handler {
@Override
public void doHandler(Member member) {
if (!"James".equals(member.getLoginName())){
System.out.println("用户名不存在");
return;
}
System.out.println("登录成功");
member.setRoleName("管理员");
chain.doHandler(member);
}
}
public class AuthHandler extends Handler {
@Override
public void doHandler(Member member) {
if (!"管理员".equals(member.getRoleName())) {
System.out.println("您不是管理员,没有权限");
return;
}
System.out.println("您是管理员,允许操作");
}
}

public class MemberService {
public void login(String loginName, String loginPass) {
// 构建一条链式处理
Handler.Builder builder = new Handler.Builder()
.addHandler(new ValidateHandler())
.addHandler(new LoginHandler())
.addHandler(new AuthHandler());
// 从第一个处理类执行到最后一个处理类
builder.builder().doHandler(new Member("James11", "1234"));
}
public static void main(String[] args) {
MemberService memberService = new MemberService();
memberService.login("Ja1mes", "1234");
}
}

责任链模式在Spring中的应用

过滤器,拦截器。
过滤器,可以配置多个过滤器来干不同的事情,然后一个一个执行。
FilterChain。
在这里插入图片描述


迭代器模式

推荐阅读
  • Java太阳系小游戏分析和源码详解
    本文介绍了一个基于Java的太阳系小游戏的分析和源码详解。通过对面向对象的知识的学习和实践,作者实现了太阳系各行星绕太阳转的效果。文章详细介绍了游戏的设计思路和源码结构,包括工具类、常量、图片加载、面板等。通过这个小游戏的制作,读者可以巩固和应用所学的知识,如类的继承、方法的重载与重写、多态和封装等。 ... [详细]
  • Iamtryingtomakeaclassthatwillreadatextfileofnamesintoanarray,thenreturnthatarra ... [详细]
  • Java容器中的compareto方法排序原理解析
    本文从源码解析Java容器中的compareto方法的排序原理,讲解了在使用数组存储数据时的限制以及存储效率的问题。同时提到了Redis的五大数据结构和list、set等知识点,回忆了作者大学时代的Java学习经历。文章以作者做的思维导图作为目录,展示了整个讲解过程。 ... [详细]
  • JavaSE笔试题-接口、抽象类、多态等问题解答
    本文解答了JavaSE笔试题中关于接口、抽象类、多态等问题。包括Math类的取整数方法、接口是否可继承、抽象类是否可实现接口、抽象类是否可继承具体类、抽象类中是否可以有静态main方法等问题。同时介绍了面向对象的特征,以及Java中实现多态的机制。 ... [详细]
  • 本文讨论了一个关于cuowu类的问题,作者在使用cuowu类时遇到了错误提示和使用AdjustmentListener的问题。文章提供了16个解决方案,并给出了两个可能导致错误的原因。 ... [详细]
  • [大整数乘法] java代码实现
    本文介绍了使用java代码实现大整数乘法的过程,同时也涉及到大整数加法和大整数减法的计算方法。通过分治算法来提高计算效率,并对算法的时间复杂度进行了研究。详细代码实现请参考文章链接。 ... [详细]
  • 本文介绍了一个Java猜拳小游戏的代码,通过使用Scanner类获取用户输入的拳的数字,并随机生成计算机的拳,然后判断胜负。该游戏可以选择剪刀、石头、布三种拳,通过比较两者的拳来决定胜负。 ... [详细]
  • 本文讨论了如何优化解决hdu 1003 java题目的动态规划方法,通过分析加法规则和最大和的性质,提出了一种优化的思路。具体方法是,当从1加到n为负时,即sum(1,n)sum(n,s),可以继续加法计算。同时,还考虑了两种特殊情况:都是负数的情况和有0的情况。最后,通过使用Scanner类来获取输入数据。 ... [详细]
  • 阿,里,云,物,联网,net,core,客户端,czgl,aliiotclient, ... [详细]
  • 本文介绍了在Java中gt、gtgt、gtgtgt和lt之间的区别。通过解释符号的含义和使用例子,帮助读者理解这些符号在二进制表示和移位操作中的作用。同时,文章还提到了负数的补码表示和移位操作的限制。 ... [详细]
  • 本文主要解析了Open judge C16H问题中涉及到的Magical Balls的快速幂和逆元算法,并给出了问题的解析和解决方法。详细介绍了问题的背景和规则,并给出了相应的算法解析和实现步骤。通过本文的解析,读者可以更好地理解和解决Open judge C16H问题中的Magical Balls部分。 ... [详细]
  • 本文介绍了如何在给定的有序字符序列中插入新字符,并保持序列的有序性。通过示例代码演示了插入过程,以及插入后的字符序列。 ... [详细]
  • C# 7.0 新特性:基于Tuple的“多”返回值方法
    本文介绍了C# 7.0中基于Tuple的“多”返回值方法的使用。通过对C# 6.0及更早版本的做法进行回顾,提出了问题:如何使一个方法可返回多个返回值。然后详细介绍了C# 7.0中使用Tuple的写法,并给出了示例代码。最后,总结了该新特性的优点。 ... [详细]
  • 从零学Java(10)之方法详解,喷打野你真的没我6!
    本文介绍了从零学Java系列中的第10篇文章,详解了Java中的方法。同时讨论了打野过程中喷打野的影响,以及金色打野刀对经济的增加和线上队友经济的影响。指出喷打野会导致线上经济的消减和影响队伍的团结。 ... [详细]
  • 猜字母游戏
    猜字母游戏猜字母游戏——设计数据结构猜字母游戏——设计程序结构猜字母游戏——实现字母生成方法猜字母游戏——实现字母检测方法猜字母游戏——实现主方法1猜字母游戏——设计数据结构1.1 ... [详细]
author-avatar
137381372_e57647
这个家伙很懒,什么也没留下!
PHP1.CN | 中国最专业的PHP中文社区 | DevBox开发工具箱 | json解析格式化 |PHP资讯 | PHP教程 | 数据库技术 | 服务器技术 | 前端开发技术 | PHP框架 | 开发工具 | 在线工具
Copyright © 1998 - 2020 PHP1.CN. All Rights Reserved | 京公网安备 11010802041100号 | 京ICP备19059560号-4 | PHP1.CN 第一PHP社区 版权所有