Head First 设计模式 --3 装饰者模式 开闭原则
装饰者模式:动态的将责任附加到对象上,若要扩展功能,装饰者提供了比集成更有弹性的替代方案。
设计原则:
1:封装变化
2:多用组合,少用继承
3:针对接口编程,不针对实现编程
4:为对象之间的松耦合设计而努力
5:对修改关闭,对扩展开放
用Head First 设计模式中的例子。
一个咖啡店,会有各种类型的咖啡,还会给咖啡加上各种辅料,计算价钱的时候当然要加上辅料的价钱。
显然,可能不可能为每一种可能性的咖啡都写一个方法。类似于这种问题,就可以用到装饰者模式类解决。
直接看代码
abstract class Beverage {
String description = "Unkwnown Beverage";
public String getDescripion() {
return description;
}
public abstract double cost();
}
abstract class CondimentDecorator extends Beverage {
public abstract String getDescripion();
}
class Espresso extends Beverage {
public Espresso() {
description = "Espresso";
}
@Override
public double cost() {
return 1.00;
}
}
class HouseBlend extends Beverage {
public HouseBlend() {
description = "House Blend Coffee";
}
@Override
public double cost() {
return 0.70;
}
}
class Mocha extends CondimentDecorator {
Beverage beverage;
public Mocha(Beverage beverage) {
this.beverage = beverage;
}
@Override
public String getDescripion() {
return this.beverage.getDescripion() + ", Mocha";
}
@Override
public double cost() {
return 0.20 + beverage.cost();
}
}
public class Test {
public static void main(String[] args) {
Beverage beverage = new Espresso();
beverage = new Mocha(beverage);
beverage = new Mocha(beverage);
System.out.println(beverage.getDescripion() + "$" + beverage.cost());
}
}
类图:

这个例子上要表达的是什么意思?开始,咖啡只有一个cost方法,我们通过用装饰者模式给每种咖啡扩展了一个getDescription方法,同时又扩展了cost方法,现在这个cost方法是选择一个基础咖啡在继续加辅料把所有的钱加载一起。
设计原则:对修改关闭,对扩展开放(开闭原则)。
我们写代码的时候遵循设计原则固然是好的,但是不要为了遵循设计原则而去用设计原则,我们用这些原则的目的就是为了帮我们设计出更好代码,如果因为遵循了设计模式而让代码变的复杂,而且这个地方以后基本上也不会有什么扩展,那么就可以考虑不用这个设计模式。换句话说就是我们无法保证每个地方都应用设计模式,我们只需要在有可能改变的地方进行设计,而哪个是以后需要改变的地方,就看实际项目而定了。
还有一个之前说多的问题,组合优于继承,那么这个地方怎么还用到了继承。要明白,“组合优于继承”中的继承说的是利用集成获得了父类的行为(依赖继承)。而装饰者模式中用到的继承是未了让装饰者与被装饰者具有相同的类型(类型匹配),以便能让装饰者取代被装饰者。这里的行为来自装饰者(CondimentDecorator及其子类)和组件(各种咖啡)。如果是依赖继承,类的行为只能在编译时就决定。而装饰者模式可以在运行时,实现新的装饰者来增加新的行为。这里Beverage可以是一个抽象类,当然也可以设计成一个接口。
装饰者模式有能力为设计注入弹性,但是也有问题,上面的代码可以看到,会加入大量的类,而导致可能一般时候会看不懂。
Head First 设计模式 --3 装饰者模式 开闭原则的更多相关文章
- ZT 设计模式六大原则(6):开闭原则
ZT 设计模式六大原则(6):开闭原则 分类: 设计模式 2012-02-27 08:48 24870人阅读 评论(72) 收藏 举报 设计模式扩展框架编程测试 定义:一个软件实体如类.模块和函数应该 ...
- 【设计模式六大原则6】开闭原则(Open Close Principle)
定义:一个软件实体如类.模块和函数应该对扩展开放,对修改关闭. 问题由来:在软件的生命周期内,因为变化.升级和维护等原因需要对软件原有代码进行修改时,可能会给旧代码中引入错误,也可能会使我们不得不 ...
- 设计模式原则(6)--Open-Closed Principle(OCP)--开闭原则
作者QQ:1095737364 QQ群:123300273 欢迎加入! 1.定义: 一个软件实体应当对扩展开放,对修改关闭.即软件实体应尽量在不修改原有代码的情况下进行扩展. 2.使用场 ...
- 设计模式六大原则(六): 开闭原则(Open Closed Principle)
定义: 一个软件实体如类.模块和函数应该对扩展开放,对修改关闭. 问题由来: 在软件的生命周期内,因为变化.升级和维护等原因需要对软件原有代码进行修改时,可能会给旧代码中引入错误,也可能会使我们不得不 ...
- java设计模式学习笔记--开闭原则
基本介绍 1.开闭(ocp)原则时编程中最基础.最重要的设计原则 2.一个软件实体如类.木块和函数应该对扩展开放,对修改关闭.用抽象构建框架,用实现扩展细节.即对提供方开放,对使用方关闭. 3.当软件 ...
- 设计原则:开-闭原则(Open-Closed Principle, OCP)
开-闭原则就是软件实体应当对扩展开放,对修改关闭.(Software entities should be open for extension,but closed for modification ...
- 开闭原则(Open Closed Principle,OCP)
遵循开闭原则设计出的模块具有两个主要特征: 对于扩展是开放的(Open for extension).这意味着模块的行为是可以扩展的.当应用的需求改变时,我们可以对模块进行扩展,使其具有满足那些改变的 ...
- php设计模式八-----装饰器模式
1.介绍: 装饰器模式(Decorator Pattern)允许向一个现有的对象添加新的功能,同时又不改变其结构.这种类型的设计模式属于结构型模式,它是作为现有的类的一个包装. 这种模式创建了一个装饰 ...
- Java设计模式 - - 单例模式 装饰者模式
Java设计模式 单例模式 装饰者模式 作者 : Stanley 罗昊 [转载请注明出处和署名,谢谢!] 静态代理模式:https://www.cnblogs.com/StanleyBlogs/p/1 ...
随机推荐
- MongoDB安装并设置为windows服务以使其开机自启
在MongoDB的官方下载windows平台的压缩zip文件,地址:https://www.mongodb.org/dr/fastdl.mongodb.org/win32/mongodb-win32- ...
- APP在iOS和Android的推送规则
因为iOS和Android不同的规则,下边将iOS和Android能接收到通知的详细情 形进行说明(前提:APP已经在设备上安装并登录过): iOS: APP未 ...
- JS的URL编码
背景 URL只能使用英文字母.阿拉伯数字和某些标点符号,不能使用其他文字和符号,这是网络标准: 只有字母和数字[-9a-zA-Z].一些特殊符号"$-_.+!*'(),"[不包括双 ...
- js 点赞数 处理
likeNum(num) { if (num === 0) { num = ''; } else if (num > 9999 && num <= 9999999) { n ...
- 9.请写出PHP5权限控制修饰符
1.public:public表明该数据成员.成员函数是对所有用户开放的,所有用户都可以直接进行调用 2.private:private表示私有,私有的意思就是除了class自己之外,任何人都不可以直 ...
- 助手系列之连接mysql数据库
import MySQLdbdef main(): try: conn=MySQLdb.connect(host='127.0.0.1',user='root',passwd='pass',db='a ...
- JQuery基础二
1.表单过滤器 <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www ...
- CSS 笔记二(Text/Fonts/Links/Lists)
CSS Text 1> Text Color used to set the color of the text 2> Text Alignment used to set the hor ...
- mina IoBuffer 常用方法
Limit(int) 如果position>limit, position = limit,如果mark>limit, 重置mark Mark() 取当前的position的快照标记mar ...
- [已解决] java.net.InetAddress.getHostName() 阻塞问题
在学习java nio的过程中发现某些情况下使用该方法会导致程序阻塞,(情况:服务器,Linux:客户端,WIN10) java.net.InetAddress.getHostName() 阻塞情况如 ...