[toc]
## 举个例子
> 水是世界上最奇特的物质之一,不仅滋润万物,更是变化万千。
> 你很难想象冰、水、气其实是同一个东西 H2O,
> 看到冰你可能更会联想到玻璃、石头,
> 看到水你可能更会联想到牛奶、可乐,
> 看到气可能更会联想到空气、氧气。
> 三个不同状态下的水好像是三种不同的东西。
![](https://box.kancloud.cn/de885e43d5844caedd4efbc04189ecaf_737x488.png)
## 代码展示
```php
<?php
class Water {
private $temperature;
private $state;
public function __construct($state) {
$this->temperature = 25;
$this->state = $state;
}
public function setState($state) {
$this->state = $state;
}
public function changeState($state) {
if ($this->state) {
echo "由" . $this->state->getStateName() . "变为" . $state->getStateName() . ',';
} else {
echo "初始化为" . $state->getStateName() . ',';
}
$this->state = $state;
}
public function getTemperature() {
return $this->temperature;
}
public function setTemperature($temperature) {
$this->temperature = $temperature;
if ($this->temperature <= 0) {
$this->changeState(new SolidState("固态"));
} elseif ($this->temperature <= 100) {
$this->changeState(new LiquidState("液态"));
} else {
$this->changeState(new GaseousState("气态"));
}
}
public function riseTemperature($step) {
$this->setTemperature($this->temperature + $step);
}
public function reduceTemperature($step) {
$this->setTemperature($this->temperature - $step);
}
public function behavior() {
$this->state->behavior($this);
}
}
class State {
private $name;
public function __construct($name) {
$this->name = $name;
}
public function getStateName() {
return $this->name;
}
public function behavior($water) {
}
}
class SolidState extends State {
public function behavior($water) {
echo "我性格高冷,当前体温" . $water->getTemperature() . "摄氏度,我坚如钢铁,仿如一冷血动物,请用我砸人,嘿嘿……" . PHP_EOL;
}
}
class LiquidState extends State {
public function behavior($water) {
echo "我性格温和,当前体温" . $water->getTemperature() . "摄氏度,我可滋润万物,饮用我可让你活力倍增……" . PHP_EOL;
}
}
class GaseousState extends State {
public function behavior($water) {
echo "我性格热烈,当前体温" . $water->getTemperature(), "摄氏度,飞向天空是我毕生的梦想,在这你将看不到我的存在,我将达到无我的境界……" . PHP_EOL;
}
}
$water = new Water(new LiquidState("液态"));
$water->behavior();
$water->setTemperature(-4);
$water->behavior();
$water->riseTemperature(18);
$water->behavior();
$water->riseTemperature(110);
$water->behavior();
$water->setTemperature(60);
$water->behavior();
$water->reduceTemperature(80);
$water->behavior();
```
```
D:\soft\php72\php.exe D:\project\php_dp\index.php
我性格温和,当前体温25摄氏度,我可滋润万物,饮用我可让你活力倍增……
由液态变为固态,我性格高冷,当前体温-4摄氏度,我坚如钢铁,仿如一冷血动物,请用我砸人,嘿嘿……
由固态变为液态,我性格温和,当前体温14摄氏度,我可滋润万物,饮用我可让你活力倍增……
由液态变为气态,我性格热烈,当前体温124摄氏度,飞向天空是我毕生的梦想,在这你将看不到我的存在,我将达到无我的境界……
由气态变为液态,我性格温和,当前体温60摄氏度,我可滋润万物,饮用我可让你活力倍增……
由液态变为固态,我性格高冷,当前体温-20摄氏度,我坚如钢铁,仿如一冷血动物,请用我砸人,嘿嘿……
Process finished with exit code 0
```
## 什么是状态模式?
> 状态即事物所处的某一种形态。
> 状态模式是说一个对象在其内部状态发生改变时,其表现的行为和外在属性不一样,这个对象看上去就像是改变了它的类型一样。
> 状态模式又称为对象的行为模式。
![](https://box.kancloud.cn/5454adf663bfa4c8360b7fa5f3649a64_664x321.png)
## 应用场景
1. 一个对象的行为取决于它的状态,并且它在运行时可能经常改变它的状态从而改变它的行为。
1. 一个操作中含有庞大的多分支的条件语句,且这些分支依赖于该对象的状态,且每一个分支的业务逻辑非常复杂时,我们可以使用状态模式来拆分他不同分支逻辑,使程序有更好的可读性可维护性。