状态模式(行为型)

一:相关定义

状态模式:允许对象在内部状态改变时改变它的行为,对象看起来好像修改了它的类。

二:相关类图和示例

状态模式类图:
状态模式类图
状态模式和策略模式类图基本一致,而差别就在于它们的“意图”。我们将一群行为封装在状态对象中,context的行为随时可委托到那些状态对象中的一个。随时间流逝,当前状态在状态对象集合中游走改变,以反映出context内部的状态。

状态模式示例图:
状态模式示例
这里以一个糖果机的状态转换作为示例来说明状态模式的应用,
糖果状态
在图中,糖果机对应于4种状态(不一定哦,可能会有后续的需求变更),通过不同的动作,糖果机会在这几种状态之间进行转换。在最简单的实现中,我们可以在糖果机类中定义这4种状态,然后在相关的行为方法中,通过if-else来进行状态的转换;但是,当需求进行变更时,例如多增加一种状态,我们就得在原有的糖果机代码中进行大范围的变更工作了,状态越来越多,if-else也越来越多,就越难以进行维护;下面看我们利用状态模式实现的糖果机。

public class GumballMachine {
    State noQuarterState;
    State hasQuarterState;
    State soldState;
    State soldOutState;

    State state = soldOutState;
    int count = 0;

    public  GumballMachine(int numberGumballs){
        noQuarterState = new NoQuarterState(this);
        hasQuarterState = new hasQuarterState(this);
        soldState = new SoldState(this);
        soldOutState = new soldOutState(this);
    }

    public void insertQuarter(){
        state.insertQuarter();
    }
    public void ejectQuarter(){
        state.ejectQuarter();
    }
    public void turnCrank(){
        state.turnCrank();
        state.dispense();
    }

    void setState(State state){
        this.state = state;
    }
    void releaseBall(){
        System.out.println("A gumball comes rolling out the slot...");
        if(count != 0){
            count = count - 1;
        }
    }
    //每个状态的getter
}

我们用4个状态类来表示糖果机的4中状态,并将动作的调用委托给糖果机现在的状态去执行,下面是列举的两种状态:

public interface State {
    void insertQuarter();   //投入25分钱
    void ejectQuarter();    //退出25分钱
    void turnCrank();        //转动曲柄
    void dispense();        //发放糖果
}

没有25分钱

public class NoQuarterState implements State {
    GumballMachine gumballMachine;

    public NoQuarterState(GumballMachine gumballMachine){
        this.gumballMachine = gumballMachine;
    }

    @Override
    public void insertQuarter() {
        System.out.println("you inserted a quarter");
        gumballMachine.setState(gumballMachine.getHasQuarterState());
    }
    @Override
    public void ejectQuarter() {
        System.out.println("you haven't inserted a quarter");
    }
    @Override
    public void turnCrank() {
        System.out.println("you turned, but there's no quarter");
    }
    @Override
    public void dispense() {
        System.out.println("you need to pay first");
    }
}

有25分钱

public class HasQuarterState implements State {
    GumballMachine gumballMachine;

    public HasQuarterState(GumballMachine gumballMachine){
        this.gumballMachine = gumballMachine;
    }

    @Override
    public void insertQuarter() {
        System.out.println("you can't insert another quarter");
    }
    @Override
    public void ejectQuarter() {
        System.out.println("Quarter returned");
        gumballMachine.setState(gumballMachine.getNoQuarterState());
    }
    @Override
    public void turnCrank() {
        System.out.println("you turned...");
        gumballMachine.setState(gumballMachine.getSoldState);
    }
    @Override
    public void dispense() {
        System.out.println("no gumball dispensed");
    }
}

售出糖果和糖果售罄状态类似,这里就不详述了。到这里,我们的状态模式就暂时告一段落了。

参考书籍:《head first 设计模式》

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值