今天,介绍一下策略模式。
策略模式是一种定义一系列算法的方法,从概念上来看,所有这些算法完成的都是相同的工作,只是实现不同,它可以以相同的方式调用所有的算法,减少了各种算法类与使用类之间的耦合。
下面我把策略模式的类层次结构图展示如下:
如图所示,Strategy类层次为Context定义了一系列的可供重用的算法和行为,继承有助于析取出这些算法中的公共功能。下面我用一个普通超市里收费的例子简单模拟了这个模式。我把其中对应的类介绍一下:
-
Context类-------------------------CashContext类
-
Strategy类---------------------------CashSuper类
-
ConcreteStrategyA类-------------CashNormal类
-
ConcreteStrategyB类-------------CashRebate类
-
ConcreteStrategyC类-------------CashReturn类
好的,上面就是将要向大家展示的Objective C源代码类。
下面,我把上面对应的类展示出来,供大家参考:
-
CashContext类接口
1
2
3
4
5
6
7
8
9
10
|
#import
<Foundation/Foundation.h> #import
"CashSuper.h" @interface CashContext: NSObject { @private CashSuper
*cs; } -(CashContext*)MyInit:( int )Types; -( void )SetCashSuper:(CashSuper*)cashSuper; -( double )GetResult:( double )money; @end |
-
CashContext类实现
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
|
#import
"CashContext.h" #import
"CashNormal.h" #import
"CashRebate.h" #import
"CashReturn.h" @implementation CashContext -(CashContext*)MyInit:( int )Types{ int myTypes; myTypes
= Types; switch (myTypes)
{ case1: [ self SetCashSuper:[[CashNormalalloc]init]]; break ; case2: [ self SetCashSuper: [[CashReturnalloc]MyInit:300
And:100]]; break ; case3: [ self SetCashSuper:[[CashRebatealloc]MyInit:0.8]]; break ; default : break ; } return self ; } -( void )SetCashSuper:(CashSuper*)cashSuper{ cs
= cashSuper; } -( double )GetResult:( double )money{ return [cs
AcceptCash:money]; } @end |
-
CashSuper类接口
1
2
3
4
5
|
#import
<Foundation/Foundation.h> @interface CashSuper: NSObject -( double )AcceptCash:( double )money; @end |
-
CashSuper类实现
1
2
3
4
5
6
7
8
9
|
#import"CashSuper.h" @implementation CashSuper -( double )AcceptCash:( double )money{ return -1.0;
//这里返回
-1.0无任何意义,只是为了定义此方法 } @end |
-
CashNormal类接口
1
2
3
4
5
|
#import"CashSuper.h" @interface CashNormal
:CashSuper @end |
-
CashNormal类实现
1
2
3
4
5
6
7
8
9
|
#import"CashNormal.h" @implementation CashNormal -( double )AcceptCash:( double )money{ return money; } @end |
-
CashRebate类接口
1
2
3
4
5
6
7
8
|
#import"CashSuper.h" @interface CashRebate:CashSuper{ @private double
moneyRebate; } @property double
moneyRebate; -(CashRebate*)MyInit:( double )moneyRebates; @end |
-
CashRebate类实现
1
2
3
4
5
6
7
8
9
10
11
12
13
14
|
#import"CashRebate.h" @implementation CashRebate @synthesize moneyRebate; -(CashRebate*)MyInit:( double )moneyRebates{ [ self setMoneyRebate:moneyRebates]; return self ; } -( double )AcceptCash:( double )money{ return moneyRebate*money; } @end |
-
CashReturn类接口
1
2
3
4
5
6
7
8
9
10
|
#import
"CashSuper.h" @interface CashReturn:CashSuper{ @private double
moneyCondition; @private double
moneyReturn; } @property double
moneyCondition; @property double
moneyReturn; -(CashReturn*)MyInit:( double )moneyConditions
And:( double )moneyReturns; @end |
-
CashReturn类实现
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
|
#import
"CashReturn.h" @implementation CashReturn @synthesize moneyReturn; @synthesize moneyCondition; -(CashReturn*)MyInit:( double )moneyConditions
And:( double )moneyReturns{ [ self setMoneyReturn:moneyReturns]; [ self setMoneyCondition:moneyConditions]; return self ; } -( double )AcceptCash:( double )money{ double result; result
= money; @try { if (money
>=moneyCondition){ result
= money - (money /moneyCondition)*moneyReturn; } } @catch ( NSException *exception)
{ NSLog (@ "Oh!Man!!CashReturn
has something wrong!" ); } @finally { return result;
} } @end |
-
Main方法调用
1
2
3
4
5
6
7
8
9
10
11
12
13
|
#import
<Foundation/Foundation.h> #import
"CashContext.h" int main
( int argc,
const char
*argv[]) { @autoreleasepool { CashContext
*cc = [[CashContext alloc]MyInit:3]; double total; total
= [cc GetResult:400]; NSLog (@ "Total
Money 400,the resual is %f" ,
total); } return 0; } |
以上是对应的策略模式中相应的类,有一点需要声明的是,这些代码是在有ARC环境下书写的,所以不需要手动释放其中的资源。所以有些传递指针地方没有进行手动释放,在此解释一下。
什么情况下需要用策略模式呢,其实我的理解是,当我们在分析需求的过程中,需要在不同时间应用不同的业务规则,就可以考虑使用策略模式处理这种变化的可能性。另外,策略模式的优点是简化了单元测试,因为每个算法都有自己的类,可以通过自己的接口单独测试。