Design patterns learning summary (XXIII) - state mode

definition

In many cases, the behavior of an object depends on the nature of its change in one or more of these properties we call the state this object called state objects. For the state object it, its behavior depends on its state, for example, you want to book a room, then only when the room is empty you can book, you want to stay in the room only when you book the room or the room is empty Time. For such an object, when it is an external event to interact when its internal state will change, so that his behavior will change accordingly.

State mode is to allow the object to change its behavior in the internal state of change, it appears to modify its class.

Character

  • Context: Environmental. It may include some internal state.

  • State: abstract class status. State defines a particular common interface for all states, any state that implements the same interface, so that, between the states can be converted to each other.

  • ConcreteState: specific state category. Specific class status for processing requests from Context, and each provides a ConcreteState implement its own request, so when Context change state behavior will also change.

Advantages and disadvantages

advantage

  • Packaging conversion rules.
  • Enumeration of possible states, need to determine the status of species in the state before the enumeration.
  • All with a state-related behavior into a class, and you can easily add new state, only need to change the state of an object can change the behavior of the object.
  • Allows the state transition logic state of the object in one, rather than one huge conditional statement block.
  • Environment allows multiple objects share a state object, thereby reducing the number of objects in the system.

Shortcoming

  • Bound state pattern is used to increase the number of system classes and objects.
  • Structure and implementation of the state model are more complex, if used improperly will lead to chaos and structure of the program code.
  • State mode support "on-off principle" is not very good for the state of the mode can be switched states, adding new classes need to modify the source code status of those responsible for state transitions, or can not switch to the new state; and a modified behavioral state classes must be amended source code corresponding to the class.

Examples

For example in a video playback state

Video Status abstract class:

public abstract class VideoStatus {

    protected VideoContext videoContext;


    public void setVideoContext(VideoContext videoContext) {
        this.videoContext = videoContext;
    }

    /**
     * 播放
     */
    public abstract void play();

    /**
     * 暂停
     */
    public abstract void pause();

    /**
     * 加速
     */
    public abstract void speed();

    /**
     * 终止
     */
    public abstract void stop();
}

Specific implementation class:

/**
 * 播放状态
 */
public class PlayStatus extends VideoStatus {

    @Override
    public void play() {
        System.out.println("视频正在播放中......");
    }

    @Override
    public void pause() {
        super.videoContext.setVideoStatus(VideoContext.PAUSE_STATUS);
    }

    @Override
    public void speed() {
        super.videoContext.setVideoStatus(VideoContext.SPEED_STATUS);
    }

    @Override
    public void stop() {
        super.videoContext.setVideoStatus(VideoContext.STOP_STATUS);
    }
}

/**
 * 暂停状态
 */
public class PauseStatus extends VideoStatus {
    @Override
    public void play() {
        super.videoContext.setVideoStatus(VideoContext.PLAY_STATUS);
    }

    @Override
    public void pause() {
        System.out.println("视频暂停播放......");
    }

    @Override
    public void speed() {
        System.out.println("错误:视频当前已暂停播放,不能加速");
    }

    @Override
    public void stop() {
        super.videoContext.setVideoStatus(VideoContext.STOP_STATUS);
    }
}

/**
 * 加速状态
 */
public class SpeedStatus extends VideoStatus {
    @Override
    public void play() {
        System.out.println("错误:视频当前已再播放中");
    }

    @Override
    public void pause() {
        super.videoContext.setVideoStatus(VideoContext.PAUSE_STATUS);
    }

    @Override
    public void speed() {
        System.out.println("视频加速播放中......");
    }

    @Override
    public void stop() {
        super.videoContext.setVideoStatus(VideoContext.STOP_STATUS);
    }
}


/**
 * 停止状态
 */
public class StopStatus extends VideoStatus {
    @Override
    public void play() {
        super.videoContext.setVideoStatus(VideoContext.PLAY_STATUS);
    }

    @Override
    public void pause() {
        System.out.println("错误:视频当前已停止播放,不能暂停");
    }

    @Override
    public void speed() {
       System.out.println("错误:视频当前已停止播放,不能加速");
    }

    @Override
    public void stop() {
        System.out.println("视频停止播放......");
    }
}

Context object:

public class VideoContext {

    private VideoStatus videoStatus;
    public static final PlayStatus PLAY_STATUS = new PlayStatus();
    public static final PauseStatus PAUSE_STATUS = new PauseStatus();
    public static final SpeedStatus SPEED_STATUS = new SpeedStatus();
    public static final StopStatus STOP_STATUS = new StopStatus();

    public VideoStatus getVideoStatus() {
        return videoStatus;
    }

    public void setVideoStatus(VideoStatus videoStatus) {
        this.videoStatus = videoStatus;
        this.videoStatus.setVideoContext(this);
    }

    /**
     * 播放
     */
    public  void play(){
        this.videoStatus.play();
    }

    /**
     * 暂停
     */
    public void pause(){
        this.videoStatus.pause();
    }

    /**
     * 加速
     */
    public  void speed(){
        this.videoStatus.speed();
    }

    /**
     * 终止
     */
    public  void stop(){
        this.videoStatus.stop();
    }
}

test:

public static void main(String[] args) {
    VideoContext videoContext = new VideoContext();
    videoContext.setVideoStatus(new PlayStatus());
    System.out.println("当前视频状态:" +videoContext.getVideoStatus().getClass().getSimpleName());
    videoContext.speed();
    System.out.println("当前视频状态:" +videoContext.getVideoStatus().getClass().getSimpleName());
    videoContext.stop();
    System.out.println("当前视频状态:" +videoContext.getVideoStatus().getClass().getSimpleName());
    videoContext.speed();
    System.out.println("当前视频状态:" +videoContext.getVideoStatus().getClass().getSimpleName());
}

Console output:

当前视频状态:PlayStatus
当前视频状态:SpeedStatus
当前视频状态:StopStatus
错误:视频当前已停止播放,不能加速
当前视频状态:StopStatus

Guess you like

Origin www.cnblogs.com/markLogZhu/p/11582742.html