您的位置:首页 > 编程语言 > Ruby

《大话设计模式》ruby版代码:策略模式

2014-12-21 18:20 274 查看
需求:

商场收银软件,根据客户购买物品的单价和数量,计算费用,会有促销活动,打八折,满三百减一百之类的。

一,使用工厂模式。

#-*-encoding:utf-8-*-

#现金收费抽象类
classCashSuper
defaccept_cash(money)
end
end

#正常收费子类
classCashNormal<CashSuper
defaccept_cash(money)
money
end
end

#打折收费子类
classCashRebate<CashSuper
attr_accessor:mony_rebate

definitialize(mony_rebate)
@mony_rebate=mony_rebate
end

defaccept_cash(money)
money*mony_rebate
end
end

#返利收费子类
classCashReturn<CashSuper
attr_accessor:mony_condition,:mony_return

definitialize(mony_condition,mony_return)
@mony_condition=mony_condition
@mony_return=mony_return
end

defaccept_cash(money)
ifmoney>mony_condition
money-(money/mony_condition)*mony_return
end
end
end

#现金收费工厂类
classCashFactory
defself.create_cash_accept(type)
casetype
when'正常收费'
CashNormal.new()
when'打8折'
CashRebate.new(0.8)
when'满三百减100'
CashReturn.new(300,100)
end
end
end

cash0=CashFactory.create_cash_accept('正常收费')
pcash0.accept_cash(700)

cash1=CashFactory.create_cash_accept('打8折')
pcash1.accept_cash(700)

cash2=CashFactory.create_cash_accept('满三百减100')
pcash2.accept_cash(700)


做到了自定义折扣比例和满减的数量。

存在的问题:

增加活动的种类时,打五折,满五百减二百,需要在工厂类中添加分支结构。

活动是多种多样的,也有可能增加积分活动,满100加10积分,积分一定可以领取活动奖品,这时就要增加一个子类。

但是每次增加活动的时候,都要去修改工厂类,是很糟糕的处理方式,面对算法有改动时,应该有更好的办法。

二,策略模式

CashSuper和子类都是不变的,增加以下内容:


classCashContext

attr_accessor:cs

definitialize(c_super)
@cs=c_super
end

defresult(money)
cs.accept_cash(money)
end

end

type='打8折'
cs=casetype
when'正常收费'
CashContext.new(CashNormal.new())
when'打8折'
CashContext.new(CashRebate.new(0.8))
when'满三百减100'
CashContext.new(CashReturn.new(300,100))
end
pcs.result(700)


CashContext类对不同的CashSuper子类进行了封装,会返回对应的result。也就是对不同的算法进行了封装,无论算法如何变化。都可以使用result得到结果。
不过,目前有一个问题,使用者需要去做判断,来选择使用哪个算法。可以和简单工场类结合。

三,策略和简单工场结合


classCashContext

attr_accessor:cs

definitialize(type)
casetype
when'正常收费'
@cs=CashNormal.new()
when'打8折'
@cs=CashRebate.new(0.8)
when'满三百减100'
@cs=CashReturn.new(300,100)
end
end

defresult(money)
cs.accept_cash(money)
end

end

cs=CashContext.new('打8折')

pcs.result(700)


CashContext中实例化了不同的子类。(简单工厂)
将子类选择的过程转移到了内部,封装了算法(策略模式)。

调用者使用更简单,传入参数(活动类型,原价),即可得到最终的结果。
这里使用者只需要知道一个类(CashContext)就可以了,而简单工场需要知道两个类(CashFactory的accept_cash方法和CashFactory),也就是说封装的更彻底。

策略模式的优点
1,CashContext中封装了算法,这些算法都是完成相同的工作,只是实现不同,有助于抽取算法中的共工功能。
2,简化了单元测试,每个类可以单独测试,不互相影响。

简单的说策略模式就是用来封装算法的。


                                            
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: