Java设计模式(三)-装饰者模式

我们都知道,可以使用两种方式给一个类或者对象添加行为。

一是使用继承。继承是给一个类添加行为的比较有效的途径。通过使用继承,可以使得子类在拥有自身方法的同时,还可以拥有父类的方法。但是使用继承是静态的,在编译的时候就已经决定了子类的行为,我们不便于控制增加行为的方式和时机。

二是使用关联。组合即将一个对象嵌入到另一个对象中,由另一个对象来决定是否引用该对象来扩展自己的行为。这是一种动态的方式,我们可以在应用程序中动态的控制。

与继承相比,关联关系的优势就在于不会破坏类的封装性,且具有较好的松耦合性,可以使系统更加容易维护。但是它的缺点就在于要创建比继承更多的对象

一、装饰者的定义:

装饰着模式动态的将责任附加到对象上,若想要扩展功能,装饰着提供比继承更有弹性的替代方案。

二、装饰着模式的UML图:

Compoent类:抽象类,每个组件可以单独使用它,或者包装起来使用

ConcreteCompoent类:动态加载新行为的对象,继承于Compoent

Decorator类:装饰着共同实现的接口,可以使抽象类

ConcreteDecorator1、ConcreteDecorator2类:装饰实例,装饰者包着Compent

三、应用场景:

Startbuzz是以扩张速度最快的的咖啡连锁店。因为扩张太快,他们准备更新订单系统,以供应需求,他们原先的设计是这样的。

购买咖啡时,可以要求在其中加入各种调料,例如:牛奶(Milk)、豆浆(Soy)、摩卡(Mocha)。Startbuzz会根据不同的调料收取不同的费用,所以订单必须考虑到调料部分。。

这是他们的第一次尝试。。。

解决方案:

四、编写代码

Compotemt:Beverage类

	//@file:beverage.java
	public abstract class Beverage {
		String description = "Unknown Beverage";
		public String getDescription(){
			return description;
		}
		public abstract double cost();
	}

ConcreteCompotemt:Espresso类

	//浓缩咖啡
	//@file:Espresso.java
	public class Espresso extends Beverage {
	<span style="white-space:pre">	</span>public Espresso(){
			description = "Espresso";
		}
		@Override
		public double cost() {
			return 1;
		}
	}

CondimentDecorator:HouseBlend类

	//@file:HouseBlend.java  、
	//深烤烘焙
	public class HouseBlend extends Beverage {
		public HouseBlend(){
			description = "HouseBlend";
		}
		@Override
		public double cost() {
			return 0.5;
		}
	}

Decorator:CondimentDecorator类

        //@file:CondimentDecorator.java
	public abstract class CondimentDecorator extends Beverage{
		abstract public String getDescription();
	}

ConcreteDecorator:Milk类

	//file:Milk.java  牛奶味道的调料
	public class Milk extends CondimentDecorator {

		Beverage beverage;
		public Milk(Beverage beverage){
			this.beverage = beverage;
		}
		@Override
		public String getDescription() {
			return beverage.getDescription()+"-Milk";
		}
		@Override
		public double cost() {
			return beverage.cost()+2.0;
		}
	}

ConcreteDecorator:Mocha类

//摩卡味道的调料
	public class Mocha extends CondimentDecorator {
		Beverage beverage;
		public Mocha(Beverage beverage){
			this.beverage = beverage;
		}
		@Override
		public String getDescription() {
			return beverage.getDescription()+"-Mocha";
		}
		@Override
		public double cost() {
			return beverage.cost()+3.0;
		}
	}

ConcreteCDecorator:Soy类

	//豆浆味道的调料
	public class Soy extends CondimentDecorator {
		Beverage beverage;
		public Soy(Beverage beverage){
			this.beverage = beverage;
		}
		@Override
		public String getDescription() {
			return beverage.getDescription()+"-Soy";
		}
		@Override
		public double cost() {
			return beverage.cost()+4.0;
		}
	}

开始下单啦!!!

public class OrderApp {
	public static void main(String[] args) {
		Beverage  beverage1 = new HouseBlend();
		beverage1 = new Milk(beverage1);
		beverage1 = new Mocha(beverage1);
		beverage1 = new Soy(beverage1);
		System.out.println("beverage1 description:"+beverage1.getDescription()+"\ncost:"+beverage1.cost());

		Beverage  beverage2 = new Espresso();
		beverage2= new Milk(beverage2);
		beverage2 = new Mocha(beverage2);
		System.out.println("beverage2 description:"+beverage2.getDescription()+"\ncost:"+beverage2.cost());
	}
}

output:

beverage1 description:HouseBlend-Milk-Mocha-Soy

cost:9.5

beverage2 description:Espresso-Milk-Mocha

cost:6.0


Java设计模式(三)-装饰者模式,布布扣,bubuko.com

时间: 2024-10-17 13:25:01

Java设计模式(三)-装饰者模式的相关文章

java设计模式之 装饰器模式

适AT java设计模式之 装饰器模式 装饰器模式 装饰器模式(Decorator Pattern)允许向一个现有的对象添加新的功能,同时又不改变其结构. 这种类型的设计模式属于结构型模式,它是作为现有的类的一个包装. 这种模式创建了一个装饰类,用来包装原有的类,并在保持类方法签名完整性的前提下,动态给一个对象添提供了额外的功能. 我们通过下面的实例来演示装饰器模式的用法.模拟一个人从想吃饭.找饭店.享受美食.结束吃饭的过程 代码展示: 首先创建一个被修饰的接口 Eat package deco

java设计模式—Decorator装饰者模式

一.装饰者模式 1.定义及作用 该模式以对客户端透明的方式扩展对象的功能. 2.涉及角色      抽象构件角色:定义一个抽象接口,来规范准备附加功能的类. 具体构件角色:将要被附加功能的类,实现抽象构件角色接口. 抽象装饰者角色:持有对具体构件角色的引用并定义与抽象构件角色一致的接口. 具体装饰角色:实现抽象装饰者角色,负责为具体构件添加额外功能. 3.简单实现 抽象构件角色java 代码: package com.pattern.decorator2; /** * 抽象构件角色 * @aut

Java设计模式之装饰者模式

要实现装饰者模式,注意一下几点内容: 1.装饰者类要实现真实类同样的接口 2.装饰者类内有一个真实对象的引用(可以通过装饰者类的构造器传入) 3.装饰类对象在主类中接受请求,将请求发送给真实的对象(相当于已经将引用传递到了装饰类的真实对象) 4.装饰者可以在传入真实对象后,增加一些附加功能(因为装饰对象和真实对象都有同样的方法,装饰对象可以添加一定操作在调用真实对象的方法,或者先调用真实对象的方法,再添加自己的方法) 5.不用继承,   先用实例说话,最后再具体装饰者模式 假设要制造添加甜蜜素和

java设计模式之装饰者模式学习

装饰者模式 Decorator模式(别名Wrapper):动态将职责附加到对象上,若要扩展功能,装饰者提供了比继承更具弹性的代替方案. 装饰者与被装饰者拥有共同的超类,继承的目的是继承类型,而不是行为 比如现在有个方法,是过滤文字的方法 1.接口: package com.qiao.wrapper; public interface MessageBoardHandler { public String filter(String msg); } 2.继承者 package com.qiao.w

java设计模式之装饰器模式以及在java中作用

在JAVA I/O类库里有很多不同的功能组合情况,这些不同的功能组合都是使用装饰器模式实现的,下面以FilterInputStream为例介绍装饰器模式的使用  FilterInputStream和FilterOutputStream 首先,这两个都分别是InputStream和OutputStream的子类.而且,FilterInputStream和FilterOutputStream是具体的子类,实现了InputStream和OutputStream这两个抽象类中为给出实现的方法. 但是,F

java设计模式之七装饰器模式(Decorator)

顾名思义,装饰模式就是给一个对象增加一些新的功能,而且是动态的,要求装饰对象和被装饰对象实现同一个接口,装饰对象持有被装饰对象的实例,关系图如下: Source类是被装饰类,Decorator类是一个装饰类,可以为Source类动态的添加一些功能,代码如下: [java] view plaincopy public interface Sourceable { public void method(); } [java] view plaincopy public class Source im

java设计模式之装饰器模式

装饰器模式的应用场景:1.需要扩展一个类的功能.2.动态的为一个对象增加功能,而且还能动态撤销.(继承不能做到这一点,继承的功能是静态的,不能动态增删.) 源接口: 1 public interface Sourceable { 2 3 void method(); 4 } Source类: 1 public class Source implements Sourceable { 2 @Override 3 public void method() { 4 System.out.println

java 设计模式 之 装饰器模式

装饰器模式的作用 在不修改原先对象核心的功能的情况下,对功能进行增强. 增强对象的功能的途径 通过类继承的方式,对父对象进行增强操作,例如造车是父类,改装跑车,跑车加大灯,改装房车,房车加私人电影院.如图: 通过这种方式做的装饰类会因为业务的复杂性激增 2.通过装饰模式,将方法增强.如图 装饰模式架构 car :被装饰的抽象类 package javadesign.decorate; /** * 抽象小汽车 */ public interface Car { public void buildC

设计模式之装饰者模式(三)

欢迎大家的持续关注.上一次,我们结合第一篇推导出来的类图,到第二篇根据类图进行实际代码的编写,对装饰者模式有了一个整体的概念以及实战.不知道对你帮助如何呢?小编已经有门道了,看完接下来的一部分,你会恍然大悟,原来实际编码中你一直在用装饰者模式. 真实世界的装饰者:Java I/O 看到标题,是不是就很想往下看,到底是I/O中的什么呢,让你早已经拥有了装饰者模式的实践?就如书上给的描述,你第一次(还有第二次和第三次)看到这些API发出"哇"的惊叹时,放心,你不是唯一收到惊吓的人.下面,我

设计模式之装饰者模式

设计模式系列都是学习HeadFirst设计模式得出的学习心得,中间的例子也会采用书中的例子.这里有必要解释一下,在下面星巴克咖啡的例子中,有几种基本的咖啡,还有牛奶.豆浆等等可以向咖啡中添加,这里说明防止下面不懂. 今天我们来了解一下装饰者模式. 回想一下java的io包,各种stream排上倒海,初学者根本分不清楚到底怎么用,眼花缭乱.其实,它的实验遵循了装饰者设计模式.顾名思义,装饰者就可以简单的理解成用一个东西来装饰另一个东西.比如,你要做鱼吃,在你做好出国之后需要加入香菜.我们就可以简单