`
miracle9i
  • 浏览: 34626 次
  • 性别: Icon_minigender_1
  • 来自: 福州
社区版块
存档分类
最新评论

Decorator模式

阅读更多

装饰模式:用于动态地给一个对象添加一些额外的职责。

 

一种为类增加功能的方式是:继承原有的类,在重载方法上添加新的职责(或业务逻辑),其实还有一种更好的方法,即为装饰模式。

《大话设计模式》中以给人穿衣服这样的过程,展示了动态穿衣的过程:

以人作为Component:

/**
 * 例子比较简单,未使用Component的继承
 * @author guozw
 *
 */
public class Person {
	private String name;

	public void show(){
		System.out.println(this.name+" wear");
	}

	public void setName(String name) {
		this.name = name;
	}
}

衣服这一抽象类,用于装饰Person:

/**
 * 装饰类,继承并组合了Component
 * @author guozw
 *
 */
public abstract class Clothes extends Person {
	
	private Person componment;
	
	/**
	 * 进行装饰注入,形成链
	 * @param componmet
	 */
	public void Decorate(Person componmet){
		this.componment=componmet;
	}
	
	@Override
	public void show() {
		componment.show();
	}
	
}

各具体子类,覆盖超类的方法。

/**
 * 各具体子类,覆盖超类的方法
 * @author guozw
 *
 */
public class TShirt extends Clothes{
	@Override
	public void show() {
		System.out.println("T-shirt");
		super.show();
	}
}
public class BigTrousers extends Clothes {
	@Override
	public void show() {
		System.out.println("Big Trousers");
		super.show();
	}
}

 调用的过程,展现了逐步装饰和链式调用的过程

	public static void main(String[] args) {
		Person p = new Person();
		p.setName("ABC");
		TShirt t = new TShirt();
		BigTrousers bt =  new BigTrousers();
		//逐步装饰
		t.Decorate(p);
		bt.Decorate(t);
		bt.show();//链式调用
	}

调用bt.show()方法将触发多态的链式调用,此例的顺序为 bt->t->person;很明显,后加入的,先被调用。

 OK,给出下类图:

通过以上例子,我还想到了一些可以改变的地方:

  1. Decorator上可以按需包装多个component,当然这取决于具体的应用情况,但这样必须在装饰过程中依赖于构造装饰。
  2. component可以为interface,那样component就成为一个公用逻辑接口,一边成为原有业务逻辑职责持有者,一方(decorator)作为附加业务逻辑的实现者。

总结:

使用的场合:当系统需要新功能时,尤其是增加在种特定情况下才会执行的行为时,可以考虑使用装饰模式。

装饰模式将每个要装饰的功能放在单独的类中,并让这个类包装它所要装饰的对象。当需要执行特殊行为时,客户代码就可以在运行时有选择地,按顺序地使用装饰功能包装到对象。

优点:把类中的装饰功能从原有类中搬移出去,可以简化原有类,可以去除相关类中重复的装饰逻辑,可以任意组合装饰的顺序

装饰模式最大的特征即为组合并继承某个类,这是多态威力的体现。

分享到:
评论

相关推荐

Global site tag (gtag.js) - Google Analytics