大话设计模式读书笔记(十三) 状态模式

状态模式:

状态模式定义:

状态模式(State):当一个对象的内在状态改变时允许改变其行为,这个对象看起来像改变了其子类。

状态模式UMl类图:



状态模式Java代码实现

public class Context {
	//定义一个状态,并且设置该状态可以读写
	private State state;
	public State getState() {
		return state;
	}
	public void setState(State state) {
		this.state = state;
	}
	//处理请求,并设置下一个状态
	public void getResult(){
		state.handle(this);
	}
}

public interface State {
	//定义一个状态接口,并抽象处理请求和设置下一状态方法
	void handle(Context context);

}
public class ConcreteStateA implements State{

	@Override
	public void handle(Context context) {
		//设置下一个状态ConcreteStateB
		context.setState(new ConcreteStateB());
	}
	
}
public class ConcreteStateB implements State{

	@Override
	public void handle(Context context) {
		//设置下一个状态为ConcreteStateA
		context.setState(new ConcreteStateA());
	}
}

状态模式例子:

现在很多人家里的灯都有两个开关,床头开关和进门开关。两个开关都是双向开关,如果等是开着的,则按下开关后等就会熄灭,如果等是关着的,按下开关,等就会打开。下面是开关控制等开关的具体实现。
//灯类,拥有一个开关状态,并且由一个changer开关控制
public class Light {
	private Changer  changer;
	
	private String state;
	
	
	public Light(Changer changer, String state) {
		super();
		this.changer = changer;
		this.state = state;
	}

	public Changer getChanger() {
		return changer;
	}

	public void setChanger(Changer changer) {
		this.changer = changer;
	}

	public String getState() {
		return state;
	}

	public void setState(String state) {
		this.state = state;
	}
	public void changeLight(){
		changer.changeState(this);
	}
}

public interface Changer {
	//开关接口,定义开关灯的方法
	public void changeState(Light light);
}
public class ChangerOn implements Changer{
	//开关类具体实现,如果开着,则关闭,否则由关闭开关去实现
	@Override
	public void changeState(Light light) {
		if("on".equals(light.getState())){
			System.out.println("灯正在开着,现在关灯");
			light.setState("Off");
			light.setChanger(new ChangerOff());
		}else{
			light.setChanger(new ChangerOff());
			light.changeLight();
		}
	}

}
public class ChangerOff implements Changer {
	//关闭开关类具体实现,如果关着,则打开,否则由关闭开关去实现
	@Override
	public void changeState(Light light) {
		if("off".equals(light.getState())){
			System.out.println("灯正在关着,现在开灯");
			light.setState("on");
			light.setChanger(new ChangerOn());
		}else{
			light.setChanger(new ChangerOn());
			light.changeLight();
		}
	}

}

主方法:
public class Main {
	public static void main(String[] args) {
		Changer changer =new ChangerOn();
		//初始状态,灯开着
		Light light = new Light(changer, "on");
		//Light light = new Light(changer, "off");
		light.changeLight();
	}
}

自己写的例子,感觉不是特别贴切,但是一时也没有想到更好的。。。。。

------------------------------------------------分割线--------------------------------------------

状态模式和策略模式的区别:

在网上查了一些资料,感觉知乎上一个名为胖胖的大牛解释的非常好,虽然有点污。本想借鉴一下,但是不让转载,这里只能附上链接,大家可以自己去看一下。https://www.zhihu.com/question/23693088

区别:

状态模式将各个状态所对应的操作分离开来,即对于不同的状态,由不同的子类实现具体操作,不同状态的切换由子类实现,当发现传入参数不是自己这个状态所对应的参数,则自己给Context类切换状态;而策略模式是直接依赖注入到Context类的参数进行选择策略,不存在切换状态的操作。

联系:

状态模式和策略模式都是为具有多种可能情形设计的模式,把不同的处理情形抽象为一个相同的接口,符合对扩展开放,对修改封闭的原则。

还有就是,策略模式更具有一般性一些,在实践中,可以用策略模式来封装几乎任何类型的规则,只要在分析过程中听到需要在不同实践应用不同的业务规则,就可以考虑使用策略模式处理,在这点上策略模式是包含状态模式的功能的,策略模式是一个重要的设计模式。




原文地址:https://www.cnblogs.com/xsyfl/p/6842509.html