我所理解的设计模式(C++实现)——策略模式(Strategy Pattern)
概述:
每个人都要“交个人所得税”,但是“在美国交个人所得税”和“在中国交个人所得税”就有不同的算税方法。 而策略模式就是对算法进行包装,是把使用算法的责任和算法本身分割开来,委派给不同的对象管理。策略模式通常把一个系列的算法包装到一系列的策略类里面,作为一个抽象策略类的子类。用一句话来说,就是:“准备一组算法,并将每一个算法封装起来,使得它们可以互换”。
类图与实例:
Context(应用场景):
1、需要使用ConcreteStrategy提供的算法。
2、内部维护一个Strategy的实例。
3、负责动态设置运行时Strategy具体的实现算法。
4、负责跟Strategy之间的交互和数据传递。
Strategy(抽象策略类):定义了一个公共接口,各种不同的算法以不同的方式实现这个接口,Context使用这个接口调用不同的算法,一般使用接口或抽象类实现。
ConcreteStrategy(具体策略类):实现了Strategy定义的接口,提供具体的算法实现。
这里用CS里的人物作为例子,每个人都可以有几个武器,武器之间动态切换,武器拥有统一的攻击命令:
#include <iostream>
using namespace std; class WeaponBehavior
{
public:
void virtual useWeapon() = 0;
}; class AK47:public WeaponBehavior
{
public:
void useWeapon()
{
cout << "Use AK47 to shoot!" << endl;
}
}; class Knife:public WeaponBehavior
{
public:
void useWeapon()
{
cout << "Use Knife to kill!" << endl;
}
}; class Character
{
public:
Character()
{
weapon = 0;
}
void setWeapon(WeaponBehavior *w)
{
this->weapon = w;
}
void virtual fight() = 0;
protected:
WeaponBehavior *weapon;
}; class King:public Character
{
public:
void fight()
{
cout << "The king:" ;
if ( this->weapon == NULL)
{
cout << "You don't have a weapon! Please Set Weapon!" << endl;
}
else
{
weapon->useWeapon();
}
}
};
int main()
{
WeaponBehavior *ak47 = new AK47();
WeaponBehavior *knife = new Knife(); Character *kin = new King(); kin->fight();
cout << endl; kin->setWeapon(ak47);
kin->fight();
cout << endl; kin->setWeapon(knife);
kin->fight(); return 0;
}
适用性:
1,多个类只区别在表现行为不同,可以使用Strategy模式,在运行时动态选择具体要执行的行为。
2,需要在不同情况下使用不同的策略(算法),或者策略还可能在未来用其它方式来实现。
3,对客户隐藏具体策略(算法)的实现细节,彼此完全独立。
优缺点:
优点:
1,策略模式提供了管理相关的算法族的办法。策略类的等级结构定义了一个算法或行为族。恰当使用继承可以把公共的代码移到父类里面,从而避免代码重复。
2,使用策略模式可以避免使用多重条件(if-else)语句。多重条件语句不易维护,它把采取哪一种算法或采取哪一种行为的逻辑与算法或行为的逻辑混合在一起,统统列在一个多重条件语句里面,比使用继承的办法还要原始和落后。
缺点:
1,客户端必须知道所有的策略类,并自行决定使用哪一个策略类。这就意味着客户端必须理解这些算法的区别,以便适时选择恰当的算法类。换言之,策略模式只适用于客户端知道算法或行为的情况。
2,由于策略模式把每个具体的策略实现都单独封装成为类,如果备选的策略很多的话,那么对象的数目就会很可观。
和其他设计模式的区别:
1,与状态模式
在解决的问题上,状态模式是解决内在状态的改变,而策略模式是解决内部算法的改变。在解决的方法上,状态模式是自我控制状态的改变,而策略模式是由外部制定使用使用啥策略。
2,简单工厂模式
简单工厂模式是创建型模式,关注对象的创建。策略模式是行为型模式,关注行为的封装。简单工厂模式是根据不同的条件返回一个适合的类给你使用,然后调用者使用工厂类返回的类去完成相应的操作。而策略模式是必须首先创建一个想使用的类实例,然后实例被当作参数传递进去,既而通过该实例去调用不用的算法。在简单工厂模式中实现了通过条件选取一个类去实例化对象,策略模式则将选取相应对象的工作交给模式的使用者,它本身不去做选取工作。
LCL_data原创于CSDN.NET【http://blog.csdn.net/lcl_data/article/details/10255125】
更多设计模式文章请参考:我所理解的设计模式
我所理解的设计模式(C++实现)——策略模式(Strategy Pattern)的更多相关文章
- 设计模式系列之策略模式(Strategy Pattern)
意图:定义一系列的算法,把它们一个个封装起来, 并且使它们可相互替换. 主要解决:在有多种算法相似的情况下,使用 if...else 所带来的复杂和难以维护. 何时使用:一个系统有许多许多类,而区分它 ...
- 【转】设计模式 ( 十八 ) 策略模式Strategy(对象行为型)
设计模式 ( 十八 ) 策略模式Strategy(对象行为型) 1.概述 在软件开发中也常常遇到类似的情况,实现某一个功能有多种算法或者策略,我们可以根据环境或者条件的不同选择不同的算法或者策略来完成 ...
- 设计模式 ( 十八 ) 策略模式Strategy(对象行为型)
设计模式 ( 十八 ) 策略模式Strategy(对象行为型) 1.概述 在软件开发中也经常遇到类似的情况,实现某一个功能有多种算法或者策略,我们能够依据环境或者条件的不同选择不同的算法或者策略来完毕 ...
- 反馈法学习设计模式(一)——策略模式Strategy Pattern
简介(Introduction) 之前学习Java8实战时,遇到一个很好的策略模式示例.便想着借着这个示例结合反馈式的方法来,学习策略设计模式,也以便后面反复琢磨学习. 首先我们通过练习,逐步写出符合 ...
- 设计模式(一):“穿越火线”中的“策略模式”(Strategy Pattern)
在前段时间呢陆陆续续的更新了一系列关于重构的文章.在重构我们既有的代码时,往往会用到设计模式.在之前重构系列的博客中,我们在重构时用到了“工厂模式”.“策略模式”.“状态模式”等.当然在重构时,有的地 ...
- HeadFirst设计模式读书笔记(1)-策略模式(Strategy Pattern)
策略模式(Strategy Pattern): 定义了了算法簇,分别封装起来,让它们之间可以相互替换,此模式让算法的变化独立于使用算法的客户端. 第一个设计原则:找出应用中可能需要变化之处,把他们独立 ...
- 乐在其中设计模式(C#) - 策略模式(Strategy Pattern)
原文:乐在其中设计模式(C#) - 策略模式(Strategy Pattern) [索引页][源码下载] 乐在其中设计模式(C#) - 策略模式(Strategy Pattern) 作者:webabc ...
- 设计模式 - 策略模式(Strategy Pattern) 具体解释
策略模式(Strategy Pattern) 具体解释 本文地址: http://blog.csdn.net/caroline_wendy/article/details/26577879 本文版权全 ...
- 8.6 GOF设计模式四: 策略模式… Strategy Pattern
策略模式… Strategy Pattern 在POS系统中,有时需要实行价格优惠, 该如何处理? 对普通客户或新客户报全价 对老客户统一折扣5% 对大客户统一折扣10% 注:课件 ...
- 二十四种设计模式:策略模式(Strategy Pattern)
策略模式(Strategy Pattern) 介绍定义一系列的算法,把它们一个个封装起来,并且使它们可相互替换.本模式使得算法的变化可独立于使用它的客户. 示例有一个Message实体类,对它的操作有 ...
随机推荐
- MFC中全局变量的定义及使用
用MFC制作的工程由很多文件构成,它不能象一般C++程序那样随意在类外定义全局变量,在这里要想定义能被工程内多个文件共享的全局变量和函数必须用一些特殊方法才行.实际上有多种方法可以实现,这里只介绍两种 ...
- 关于安装PHP补装PDO与PDO_MYSQL操作
我这里是通过PHP源码包来安装的 1.安装pdo cd到你的PHP源码包下的ext/pdo目录,然后执行如下操作: #/usr/local/php/bin/phpize (/usr/local/p ...
- 数据库 SQL 外键约束 多表查询
多表设计与多表查询 1.外键约束 表是用来保存现实生活中的数据的,而现实生活中数据和数据之间往往具有一定的关系,我们在使用表来存储数据时,可以明确的声明表和表之前的依赖关系,命令数据库来 ...
- Avi视频生成缩略图时,提示“尝试读取或写入受保护的内存。这通常指示其他内存已损坏”
需求:录制Avi格式视频成功后,使用DirectShow生成缩略图,由于视频录制时,宽高分辨率可调节,所以有些情况下,生成缩略图会抛出异常“尝试读取或写入受保护的内存.这通常指示其他内存已损坏”. 异 ...
- (转)SQL流程控制语句学习(一):变量及控制语句种类
1.局部变量 用户自己定义的,称局部变量,以@标识. 作用范围:定义局部变量的批处理.存储过程.触发器和语句块 局部变量的定义: declare @局部变量名 数据类型 注意:变量的类型不能是text ...
- 2.Android Studio系列教程2——基本设置与运行
原文链接:http://stormzhang.com/devtools/2014/11/28/android-studio-tutorial2/ 一.项目结构 二.Android Studio ...
- 返回到上一页的html代码的几种写法
关键词:返回上一页 html代码超链接返回上一页代码: <a href=”#” onClick=”javascript :history.back(-1);”>返回上一页</a> ...
- NetBeans使用技巧记录
1.窗体字体大小设置: 在etc文件夹下的netbeans.conf中添加,12表示字体大小,12正合适. netbeans_default_options="--fontsize 12 - ...
- nodejs概论
我将在此写下自己读<Node.js开发指南>一书的笔记,以便于以后的学习. 一.什么是node.js Node.js 是一个让 JavaScript 运行在浏览器之外的平台. Node.j ...
- JAVA程序优化之字符串优化处理
字符串是软件开发中最为重要的对象之一.通常,字符串对象或其等价对象(如char数组),在内存中总是占据了最大的空间块.因此如何高效地处理字符串,必将是提高系统整体性能的关键所在. 1.String对象 ...