设计模式(8)-状态模式(关注状态之间的变化)

状态模式(State Pattern)是设计模式的一种,属于行为模式。

定义(源于Design Pattern):当一个对象的内在状态改变时允许改变其行为,这个对象看起来像是改变了其类。

  状态模式主要解决的是当控制一个对象状态的条件表达式过于复杂时的情况。把状态的判断逻辑转移到表示不同状态的一系列类中,可以把复杂的判断逻辑简化。

意图:允许一个对象在其内部状态改变时改变它的行为

适用场景:

  1.一个对象的行为取决于它的状态,并且它必须在运行时刻根据状态改变它的行为。

  2.一个操作中含有庞大的多分支结构,并且这些分支决定于对象的状态。

类图结构:

这样的话让程序更加面向对象

状态模式的好处是将与特定状态相关的行为局部化,并且将不同的状态行为分割开来。  目的就是消除庞大的分支语句,状态模式通过把各种状态转移逻辑分布到state的子类之间,  来减少相互间的依赖。  什么时候使用?  当一个对象的行为取决于它的状态,并且它必须在运行时根据状态改变它的行为时,就可以  考虑状态模式。

参考代码如下:

#ifndef _STATE_H_
#define _STATE_H_
#include <iostream>
#include <string>

using namespace std;

class Work;

class State{
public:
	virtual void writeProgram(Work* work) = 0;
};
//12 before
class ForenoonState : public State{
public:
	void writeProgram(Work* work);
};
//12 ~ 13 middle
class MoonState:public State{
public:
	void writeProgram(Work* work);
};

//12 ~ 13 middle
class AfterMoonState:public State{
public:
	void writeProgram(Work* work);
};

//晚间
class EveningState:public State{
public:
	void writeProgram(Work* work);
};
//休息
class RestState:public State{
public:
	void writeProgram(Work* work);
};
//睡觉
class SleepingState:public State{
public:
	void writeProgram(Work* work);
};

class Work{
private:
	State* m_current;
	int m_hour;
	bool m_finish;
public:
	Work(void):m_current(NULL),m_finish(false),m_hour(0){
		m_current = new ForenoonState();
	}
	int getHour(void){
		return m_hour;
	}
	void setHour(const int hour){
		m_hour = hour;
	}
	bool getIsFinished(void){
		return m_finish;
	}
	void setFinishFlag(const bool bFinished){
		m_finish = bFinished;
	}
	void setState(State* state){
		m_current = state;
	}
	void writeProgram(){
		m_current->writeProgram(this);
	}
};

void ForenoonState::writeProgram(Work* work){
	if(work->getHour()<12){
		cout<<"当前时间:"<<work->getHour()<<"点 上午工作,精神百倍"<<endl;
	}else{
		work->setState(new MoonState());
		work->writeProgram();
	}
}

void MoonState::writeProgram(Work* work){
	if(work->getHour()<13){
		cout<<"当前时间:"<<work->getHour()<<"点 午休,得去吃饭了!"<<endl;
	}else{
		work->setState(new AfterMoonState());
		//work->writeProgram();
	}
}

void AfterMoonState::writeProgram(Work* work){
	if(work->getHour()<17){
		cout<<"当前时间:"<<work->getHour()<<"点 下午状态还可以,继续努力!"<<endl;
	}else{
		work->setState(new EveningState());
		work->writeProgram();
	}
}

void EveningState::writeProgram(Work* work){
	if(work->getIsFinished()){
		work->setState(new RestState());
		work->writeProgram();
	}else{
		if(work->getHour()<21){
			cout<<"当前时间:"<<work->getHour()<<"点 加班啊,疲惫之极!"<<endl;
		}else{
			work->setState(new SleepingState());
			work->writeProgram();
		}
	}
}

void RestState::writeProgram(Work* work){
	cout<<"当前时间:"<<work->getHour()<<"点 下班回家了!"<<endl;
}

void SleepingState::writeProgram(Work* work){
	cout<<"当前时间:"<<work->getHour()<<"点 不行了睡着了!"<<endl;
}

#endif

void main(){
	Work* work = new Work();
	work->setHour(9);
	work->writeProgram();
	work->setHour(10);
	work->writeProgram();
	work->setHour(12);
	work->writeProgram();
	work->setHour(13);
	work->writeProgram();
	work->setHour(14);
	work->writeProgram();
	work->setHour(17);
	work->writeProgram();
	
	work->setFinishFlag(false);
	work->writeProgram();
	
	work->setHour(19);
	work->writeProgram();
	work->setHour(21);
	work->writeProgram();
}

对于状态频繁变更需要考虑状态模式。

本文参与腾讯云自媒体分享计划,欢迎正在阅读的你也加入,一起分享。

发表于

我来说两句

0 条评论
登录 后参与评论

相关文章

来自专栏程序员八阿哥

王老板Python面试(6):25道Python工程师面试必备知识点!

Python是一种解释型语言。这就是说,与C语言和C的衍生语言不同,Python代码在运行之前不需要编译。其他解释型语言还包括PHP和Ruby。

751
来自专栏向治洪

多线程之传统多线程

Contents 传统线程技术 传统创建线程方式 传统定时器技术 互斥 同步 传统线程技术 传统创建线程方式 1.继承Thread类,覆盖run方法 ...

2109
来自专栏WindCoder

Java设计模式学习笔记—原型模式

文章最后“Java设计模式笔记示例代码整合”为本系列代码整合,所有代码均为个人手打并运行测试,不定期更新。本节内容位于其Prototype包(package)中...

762
来自专栏西枫里博客

Python学习笔记八(函数的定义和参数)

本次学习内容同样先回顾下上次学习的序列。然后学习今天的自定义函数部分。在编程中无论是面向过程还是面向对象,函数都是不可或缺的存在。什么是函数?这个问题在任何语言...

1062
来自专栏Java技术分享

Java8的十大新特性你了解多少呢?

今天,我们先来复习一下2014年发布的Java 8的十大新特性。 Java 8可谓是自Java 5以来最具革命性的版本了,她在语言、编译器、类库、开发工具以及J...

2178
来自专栏C/C++基础

C++IO流简介

输入输出(IO)是指计算机同任何外部设备之间的数据传递。常见的输入输出设备有文件、键盘、打印机、屏幕等。数据可以按记录(或称数据块)的方式传递,也可以 流的方式...

1403
来自专栏韩伟的专栏

在C++中模拟JAVA内部类的方法

有时候我们需要把一批互相关联的API用不同的类提供给用户,以便简化每个类的使用难度。但是这样这些类之间的数据共享就成了问题。JAVA的内部类可以自由的访问外围类...

2714
来自专栏微信公众号:Java团长

优秀Java程序员的编程风格

今天突发奇想,对编码习惯和编程风格很感兴趣,于是乎,找了一下关于编程风格(Java篇)的资料,希望对爱好编码或者开始学习编码的同学有帮助!

772
来自专栏生信宝典

Python学习极简教程 (一)

Python 教程 欢迎来到Python的世界,本教程将带你遨游Python,领悟Python的魅力。本教程专注于帮助初学者,尤其是生物信息分析人员快速学会P...

47711
来自专栏blackheart的专栏

[C#6] 2-nameof 运算符

0. 目录 C#6 新增特性目录 1. 老版本的代码 1 using System; 2 namespace csharp6 3 { 4 in...

2145

扫码关注云+社区

领取腾讯云代金券