State definition: different states, different behaviors; or in other words, each state has corresponding behaviors.
When to use status mode
State mode is more commonly used in actual use and is suitable for "state switching". Because we often use If elseif else to switch states, if this judgment of state is repeated, we need to think about whether we can adopt the State mode.
Not only based on the status, but also on the attributes. If the properties of an object are different, the behavior of the object is different. This occurs frequently in the database system. We often add fields with the meaning of property attributes at the end of a data table to identify some records For records of special properties, such changes (switching) of properties may occur at any time, so it is possible to use State.
In actual use, there are many state switching similar to switches, but sometimes it is not that obvious, depending on your experience and depth of understanding of the system.
What we want to explain here is that there are some differences between "switch switching state" and "general state judgment". "general state judgment" also has an if..elseif structure, for example:
The code copy is as follows:
if (which==1) state="hello";
else if (which==2) state="hi";
else if (which==3) state="bye";
This is a "general state judgment". The difference in state value is determined based on which variable, which has nothing to do with state. If changed to:
The code copy is as follows:
if (state.euqals("bye")) state="hello";
else if (state.euqals("hello")) state="hi";
else if (state.euqals("hi")) state="bye";
This is the "switch switching state", which is to switch the state of the state from "hello" to "hi", and then to "bye"; when switching to "hello", it is like a rotary switch, and this state can be changed State mode is used.
If you simply switch the direction "hello"-->"hi"-->"bye"-->"hello" in the above, you don't necessarily need to use the State mode, because the State mode will create many subclasses. Complexity, but if another behavior occurs: switch the switching direction above inverted, or you need to switch at will, you need State.
Please see the following example:
The code copy is as follows:
public class Context{
private Color state=null;
public void push(){
//If the current red state is switched to blue
if (state==Color.red) state=Color.blue;
//If the current blue state is switched to green
else if (state==Color.blue) state=Color.green;
//If the current black state is switched to red
else if (state==Color.black) state=Color.red;
//If the current green state is switched to black
else if (state==Color.green) state=Color.black;
Sample sample=new Sample(state);
sample.operate();
}
public void pull(){
//It is exactly the opposite of push state switching if (state==Color.green) state=Color.blue;
else if (state==Color.black) state=Color.green;
else if (state==Color.blue) state=Color.red;
else if (state==Color.red) state=Color.black;
Sample2 sample2=new Sample2(state);
sample2.operate();
}
}
In the above example, we have two actions push and pull pull. These two switch actions change the Context color. At this point, we need to use the State mode to optimize it.
Also note: But in the above example, the change of state is just a simple color assignment. This specific behavior is very simple. State is suitable for huge specific behavior. Therefore, in this example, it is not necessary to use State in actual use. pattern, this will increase the number of subclasses, making it simple and complicated.
For example: bank accounts often switch between Open state and Close state.
For example: the classic TcpConnection, the state of Tcp has three states: creating listening closes and repeated conversions. The specific behavior of creating listening closes cannot be completed in just one or two sentences, and is suitable for using State.
For example: mailbox POP account will have four states, start HaveUsername Authorized quit, the corresponding behavior of each state should be relatively large, suitable for using State.
For example: selecting different tools in the toolbox can be regarded as switching between different tools, suitable for using State. For example, if you have a specific drawing program, users can choose different tools to draw the box straight curve. This state can be used to switch state.
How to use state mode
State requires two types of entities to participate:
1.state manager The state manager is a switch. For example, the Context in the above example is actually a state manager. There are state switching actions in the state manager.
2. The parent class implemented by abstract classes or interfaces, different states are inheriting different subclasses of this parent class.
Taking the above Context as an example, we want to modify it and create two types of entities.
The first step is to create a parent class:
The code copy is as follows:
public abstract class State{
public abstract void handlepush(Context c);
public abstract void handlepull(Context c);
public abstract void getcolor();
}
The methods in the parent class must correspond to the switch behavior in the state manager. In the state manager, this example is in the Context, which has two switch actions push and pull pull. Then, in the state parent class, these two actions must be handled specifically. : handlepush() handlepull(); also need a method to get color() to get push or pull results.
The following are the implementations of specific subclasses:
The code copy is as follows:
public class BlueState extends State{
public void handlepush(Context c){
// According to push method "If it is blue, switch to green";
c.setState(new GreenState());
}
public void handlepull(Context c){
// According to the pull method "If it is blue, switch to red";
c.setState(new RedState());
}
public abstract void getcolor(){ return (Color.blue)}
}
Similarly, subclasses in other states are implemented as blue.
The second step is to rewrite the State manager, which is the Context of this example:
The code copy is as follows:
ublic class Context{
private Sate state=null; //We changed the original Color state to a newly created State state;
//setState is used to change the state of state using setState to achieve state switching
pulic void setState(State state){
this.state=state;
}
public void push(){
//The details of the state switching are in this case the color change, which has been encapsulated in the handlepush of the subclass, and there is no need to care about state.handlepush(this);
//Because sample needs to use a switching result in state, use getColor()
Sample sample=new Sample(state.getColor());
sample.operate();
}
public void pull(){
state.handlepull(this);
Sample2 sample2=new Sample2(state.getColor());
sample2.operate();
}
}
At this point, we have implemented the refactoring process of State.
The above is just a fairly simple example. In practical applications, the handling of handlepush or handlelpull is complicated.