【设计模式】职责链模式--------Java

23 篇文章 0 订阅
22 篇文章 0 订阅

属于“数据结构”模式。

动机:一个请求可能被多个对象中的一个处理处理,运行时只能有一个接收者。为解决请求发送者与接收者之间的紧耦合,使多个对象都有机会处理请求,将这些对象连成一条链,并沿着这链传递请求,直到有一个对象处理它为止。

1.问题引入:(员工的加薪申请的审批)

public class Test {
	public static void main(String[] args) {
		//三个管理者
		Manager jingli=new Manager("刘刘");
		Manager zongjian=new Manager("张张");
		Manager zongjingli=new Manager("王王");
		
		//设置小菜请求加薪100
		Request request=new Request();
		request.setRequestType("加薪");
		request.setRequestContent("小菜请求加薪");
		request.setNumber(100);
		
		//不同的级别对小菜的请求进行审批
		jingli.getResult("经理", request);
		System.out.println("-------------------------------------");
		zongjian.getResult("总监", request);
		System.out.println("-------------------------------------");
		zongjingli.getResult("总经理", request);
		
		System.out.println();
		System.out.println();
		
		//设置小菜请假3天的请求
		request.setRequestType("请假");
		request.setRequestContent("小菜请假三天");
		request.setNumber(3);
		
		jingli.getResult("经理", request);
		System.out.println("-------------------------------------");
		zongjian.getResult("总监", request);
		System.out.println("-------------------------------------");
		zongjingli.getResult("总经理", request);
	}
}

//申请类
class Request {
	// 申请类别
	private String requestType;
	// 申请内容(实际没有用到)
	private String requestContent;
	// 申请数量
	private int number;

	public String getRequestType() {
		return requestType;
	}

	public void setRequestType(String requestType) {
		this.requestType = requestType;
	}

	public String getRequestContent() {
		return requestContent;
	}

	public void setRequestContent(String requestContent) {
		this.requestContent = requestContent;
	}

	public int getNumber() {
		return number;
	}

	public void setNumber(int number) {
		this.number = number;
	}

}

//管理者类
class Manager{
	//管理者姓名
	protected String name;

	public Manager(String name) {
		this.name = name;
	}
	
	//审批方法
	public void getResult(String managerLevel,Request request) {//managerLevel是管理者的职位
		System.out.println("请求类别:"+request.getRequestType()+"   请求数量:"+request.getNumber());
		if(managerLevel.equals("经理")) {
			if(request.getRequestType().equals("请假")&&request.getNumber()<=2) {
				System.out.println("请假天数<=2,被经理批准。");
			}else {
				System.out.println("经理无权批准。");
			}
		}else if(managerLevel.equals("总监")) {
			if(request.getRequestType().equals("请假")&&request.getNumber()<=5) {
				System.out.println("请假天数<=5,被总监批准。");
			}else {
				System.out.println("总监无权批准。");
			}
		}else if(managerLevel.equals("总经理")) {
			if(request.getRequestType().equals("请假")) {
				System.out.print("请假被总经理批准。");
			}else if(request.getRequestType().equals("加薪")&&request.getNumber()<=500) {
				System.out.println("加薪<=500,被总经理批准。");
			}else {
				System.out.println("加新>500,总经理无权批准。");
			}
		}
	}
}

缺点:Manager类的getResult()方法太长、有太多分支,违背了单一职责原则和开放封闭原则。

2.解决:设置管理者基类,且各个具体管理者之间有关系可以实现上报
在这里插入图片描述

public class Test {
	public static void main(String[] args) {
		// 三个管理者
		CommonManager jingli = new CommonManager("刘刘");
		MajorManager zongjian = new MajorManager("张张");
		GenerManager zongjingli = new GenerManager("王王");

		// 设置小菜请求加薪100
		Request request = new Request();
		request.setRequestType("加薪");
		request.setRequestContent("小菜请求加薪");
		request.setNumber(100);

		// 不同的级别对小菜的请求进行审批
		jingli.requestApplications(request);
		System.out.println("-------------------------------------");
		zongjian.requestApplications(request);
		System.out.println("-------------------------------------");
		zongjingli.requestApplications(request);

		System.out.println();
		System.out.println();

		// 设置小菜请假3天的请求
		request.setRequestType("请假");
		request.setRequestContent("小菜请假三天");
		request.setNumber(3);

		jingli.requestApplications(request);
		System.out.println("-------------------------------------");
		zongjian.requestApplications(request);
		System.out.println("-------------------------------------");
		zongjingli.requestApplications(request);
	}
}

//申请类
class Request {
	// 申请类别
	private String requestType;
	// 申请内容(实际没有用到)
	private String requestContent;
	// 申请数量
	private int number;

	public String getRequestType() {
		return requestType;
	}

	public void setRequestType(String requestType) {
		this.requestType = requestType;
	}

	public String getRequestContent() {
		return requestContent;
	}

	public void setRequestContent(String requestContent) {
		this.requestContent = requestContent;
	}

	public int getNumber() {
		return number;
	}

	public void setNumber(int number) {
		this.number = number;
	}

}

//管理者基类
abstract class Manager {
	// 管理者姓名
	protected String name;
	// 管理者上级
	protected Manager superior;

	public Manager(String name) {
		super();
		this.name = name;
	}

	public void setSuperior(Manager superior) {
		this.superior = superior;
	}

	public abstract void requestApplications(Request request);
}

//经理类(具体管理者)
class CommonManager extends Manager{

	public CommonManager(String name) {
		super(name);
	}

	public void requestApplications(Request request) {
		if(request.getRequestType().equals("请假")&&request.getNumber()<=2) {
			System.out.println(name+":"+request.getRequestContent()+" 数量"+request.getNumber()+" 被批准。");
		}else {
			if(superior!=null) {
				superior.requestApplications(request);
			}
		}
	}
}

//总监类(具体管理者)
class MajorManager extends Manager{

	public MajorManager(String name) {
		super(name);
	}

	public void requestApplications(Request request) {
		if(request.getRequestType().equals("请假")&&request.getNumber()<=5) {
			System.out.println(name+":"+request.getRequestContent()+" 数量"+request.getNumber()+" 被批准。");
		}else {
			if(superior!=null) {
				superior.requestApplications(request);
			}
		}
	}
}

//总经理类(具体管理者)
class GenerManager extends Manager{

	public GenerManager(String name) {
		super(name);
	}

	public void requestApplications(Request request) {
		if(request.getRequestType().equals("请假")) {
			System.out.println(name+":"+request.getRequestContent()+" 数量"+request.getNumber()+" 被批准。");
		}else if(request.getRequestType().equals("加薪")&&request.getNumber()<=500) {
			System.out.println(name+":"+request.getRequestContent()+" 数量"+request.getNumber()+" 被批准。");
		}else {
			System.out.println(name+":"+request.getRequestContent()+" 数量"+request.getNumber()+" 再说吧。");
		}
	}
}

3.职责链模式:
发出请求的客户端并不知道那个对象会最终处理这个请求。
在这里插入图片描述

public class Test {
	public static void main(String[] args) {
		//定义3个审批人
		Handler h1=new ConcreteHandler1();
		h1.setName("审批人1");
		Handler h2=new ConcreteHandler2();
		h2.setName("审批人2");
		Handler h3=new ConcreteHandler3();
		h3.setName("审批人3");
		
		//设置审批人的下一个审批人
		h1.setSuccessor(h2);
		h2.setSuccessor(h3);
		
		int[] requests= {2,5,14,22,18,3,27,20};
		for(int i=0;i<requests.length;i++) {
			//全都是从审批人1开始
			h1.handleRequest(requests[i]);
		}
	}
}

abstract class Handler {
	protected String name;
	// 继任者
	protected Handler successor;

	public void setName(String name) {
		this.name = name;
	}

	public String getName() {
		return name;
	}

	public void setSuccessor(Handler successor) {
		this.successor = successor;
	}
	
	public abstract void handleRequest(int request);
}

//具体处理者类1
class ConcreteHandler1 extends Handler{

	public void handleRequest(int request) {
		if(request>=0&&request<10) {
			System.out.println(name+"处理请求"+request);
		}else if(successor!=null) {
			successor.handleRequest(request);
		}
	}
}

//具体处理者类2
class ConcreteHandler2 extends Handler{

	public void handleRequest(int request) {
		if(request>=10&&request<20) {
			System.out.println(name+"处理请求"+request);
		}else if(successor!=null) {
			successor.handleRequest(request);
		}
	}
}

//具体处理者类3
class ConcreteHandler3 extends Handler{

	public void handleRequest(int request) {
		if(request>=20&&request<30) {
			System.out.println(name+"处理请求"+request);
		}else if(successor!=null) {
			successor.handleRequest(request);
		}
	}
}

优点:
请求是沿着链传递直至有一个ConcreteHandler对象负责处理它。请求者不用管该请求由哪个对象处理。
链中的对象也不知道链的结构,简化了对象的相互连接。

缺点:产生很多细粒度的对象;有的请求到最后也不能被处理。

本质:分离职责,动态耦合。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值