有时候,我们会遇见一些场景,里面有非常多的状态变化,各个状态下又有不同的行为,在这种情况下,如果用if-else去写程序的话,会让代码的可读性非常差,编写会非常容易出错,也不容易维护和拓展。在这种情况下,我们就要用到状态模式。
我们拿女孩多变的心情来举例吧,下面看看状态的变化图
假设女孩的心情在这四种之间自由转化(天知道有几种- -),如果我们用if-else去做,估计复杂的关系会把人逼疯,于是我们把每一种状态都封装起来,那么我们只需要专注于一个状态的行为就行了,然后再把不同的状态集成起来,这样我们就不用面对这错综复杂的关系了。
下面我们来看看该如何做,先上类图
我们定义了四个状态类,每个状态类里面都有完整的一套方法,然后在girl里面用这些方法的时候就可以直接委托给状态去做了,而不用去管什么状态,因为状态的变化被封装了起来。
下面我们来看看是如何实现的
public interface State {
//说情话
void saysWeetWords(Boy boy);
//出去玩
void hangOut();
//辱骂
void malign();
//长时间不联系
void holdOff();
//买礼物
void buyGifts();
//感动
void touch();
}
定义高富帅三个属性的男生类
public class Boy {
boolean high;
boolean rich;
boolean dashing;
public boolean isHigh() {
return high;
}
public void setHigh(boolean high) {
this.high = high;
}
public boolean isRich() {
return rich;
}
public void setRich(boolean rich) {
this.rich = rich;
}
public boolean isDashing() {
return dashing;
}
public void setDashing(boolean dashing) {
this.dashing = dashing;
}
}
不喜欢时候女生面对各种行为的反应
public class DislikeState implements State {
Girl girl;
public DislikeState(Girl girl) {
this.girl = girl;
}
@Override
public void saysWeetWords(Boy boy) {
System.out.println("你真让人恶心");
}
@Override
public void hangOut() {
System.out.println("今天有事,明天也有事,一直都很忙");
}
@Override
public void malign() {
System.out.println("不和神经病说话");
}
@Override
public void holdOff() {
girl.setCurrentState(girl.getUnhappy());
System.out.println("慢慢也没觉得那么讨厌了");
}
@Override
public void buyGifts() {
girl.setCurrentState(girl.getHappy());
System.out.println("你看起来也没那么讨厌嘛");
}
@Override
public void touch() {
girl.setCurrentState(girl.getHappy());
System.out.println("其实,有时候感觉你也挺好的");
}
}
喜欢的时候女生面对各种行为的反应
public class LikeState implements State {
Girl girl;
public LikeState(Girl girl) {
this.girl = girl;
}
@Override
public void saysWeetWords(Boy boy) {
System.out.println("净瞎说什么大实话");
}
@Override
public void hangOut() {
System.out.println("和你在一起真开心");
}
@Override
public void malign() {
girl.setCurrentState(girl.getDislike());
System.out.println("你敢凶我?不理你了");
}
@Override
public void holdOff() {
girl.setCurrentState(girl.getUnhappy());
System.out.println("这么久都不联系,不开心");
}
@Override
public void buyGifts() {
System.out.println("爱你");
}
@Override
public void touch() {
System.out.println("你是我的全世界");
}
}
开心时候的反应
public class HappyState implements State {
Girl girl;
public HappyState(Girl girl) {
this.girl = girl;
}
@Override
public void saysWeetWords(Boy boy) {
if (boy.isRich()){
girl.setCurrentState(girl.getLike());
System.out.println("喜欢^_^");
}
else {
girl.setCurrentState(girl.getDislike());
System.out.println("你是好人");
}
}
@Override
public void hangOut() {
System.out.println("今天真开心");
}
@Override
public void malign() {
girl.setCurrentState(girl.getDislike());
System.out.println("非常生气");
}
@Override
public void holdOff() {
System.out.println("内心毫无波动");
}
@Override
public void buyGifts() {
System.out.println("谢谢,我很喜欢");
}
@Override
public void touch() {
girl.setCurrentState(girl.getLike());
System.out.println("你让我很感动,我喜欢你");
}
}
不开心时候的反应
public class UnhappyState implements State {
Girl girl;
public UnhappyState(Girl girl) {
this.girl = girl;
}
@Override
public void saysWeetWords(Boy boy) {
if(boy.isRich()){
girl.setCurrentState(girl.getHappy());
System.out.println("谢谢你的安慰");
}
else {
girl.setCurrentState(girl.getDislike());
System.out.println("安静点,别吵!");
}
}
@Override
public void hangOut() {
girl.setCurrentState(girl.getHappy());
System.out.println("心情好多了");
}
@Override
public void malign() {
girl.setCurrentState(girl.getDislike());
System.out.println("神经病,再也不想见到你了");
}
@Override
public void holdOff() {
System.out.println("内心毫无波动");
}
@Override
public void buyGifts() {
girl.setCurrentState(girl.getHappy());
System.out.println("谢谢你的礼物,我很开心");
}
@Override
public void touch() {
girl.setCurrentState(girl.getLike());
System.out.println("你让我很感动,我喜欢你");
}
}
在girl类里面集成使用
public class Girl {
private State dislike;
private State like;
private State happy;
private State unhappy;
private State currentState;
private Boy boy;
public Girl(Boy boy) {
this.dislike = new DislikeState(this);
this.like=new LikeState(this);
this.happy=new HappyState(this);
this.unhappy=new UnhappyState(this);
this.currentState=this.happy;
this.boy=boy;
}
public void saysWeetWords() {
currentState.saysWeetWords(boy);
}
public void hangOut() {
currentState.hangOut();
}
public void malign() {
currentState.malign();
}
public void holdOff() {
currentState.holdOff();
}
public void buyGifts() {
currentState.buyGifts();
}
public void touch() {
currentState.touch();
}
public State getDislike() {
return dislike;
}
public State getLike() {
return like;
}
public State getHappy() {
return happy;
}
public State getUnhappy() {
return unhappy;
}
public State getCurrentState() {
return currentState;
}
public void setCurrentState(State currentState) {
this.currentState = currentState;
}
}
写个测试类
public static void main(String[] args) {
Boy boy=new Boy();
boy.setRich(true);
boy.setDashing(false);
boy.setHigh(false);
Girl girl=new Girl(boy);
girl.saysWeetWords();
girl.hangOut();
girl.malign();
girl.buyGifts();
girl.saysWeetWords();
}
运行结果:
喜欢^_^
和你在一起真开心
你敢凶我?不理你了
你看起来也没那么讨厌嘛
喜欢^_^
我们可以看到,通过这种方式,主逻辑里面没有用if-else就完成了如此复杂的状态变化,并且层次非常清晰,也十分便于拓展,当然也有缺点,那就是类膨胀。
如果你的系统内部状态变化非常多的话,建议你可以尝试使用状态模式
PS:源码地址