Decorator Pattern(装饰模式)
装饰模式:动态的给一个对象添加一些额外的职责。当然我们也可以通过继承来实现类似的功能,但是随着子类的增多,各种子类的组合会造成子类的急剧膨胀。
Requirement:
假设客户有一个要求,需要打一个report,并且report 的header 和footer 各有3种,然后要求打出所有可能组合的report。
Analysis:
当然纯粹的通过子类继承也可以实现,但是现在如果header 和footer各有10种呢,那么你就要有100个扩展类。但是通过使用装饰模式,你只要10 header 类+10个footer类(即20个类)就可以轻松搞定。下面我们以header 和footer 各有两个具体实现一下。
Sample Code:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks; namespace TestDecoratorPatternSample
{
public abstract class Report
{
public abstract void ReportContent();
} public class Content : Report
{
public override void ReportContent()
{
Console.WriteLine("This is report content.");
}
} public abstract class ReportDecorator : Report
{
private Report report;
public ReportDecorator(Report myReport)
{
report = myReport;
}
public override void ReportContent()
{
report.ReportContent();
}
}
#region Header1
public class Header1 : ReportDecorator
{
public Header1(Report myReport)
: base(myReport)
{
} public override void ReportContent()
{
ReportHeader();
base.ReportContent();
} public void ReportHeader()
{
Console.WriteLine("This is report header1.");
}
} #endregion
#region Header2 public class Header2 : ReportDecorator
{
public Header2(Report myReport)
: base(myReport)
{
} public override void ReportContent()
{
ReportHeader();
base.ReportContent();
} public void ReportHeader()
{
Console.WriteLine("This is report header2.");
}
} #endregion
#region Header3 public class Header3 : ReportDecorator
{
public Header3(Report myReport)
: base(myReport)
{
} public override void ReportContent()
{
ReportHeader();
base.ReportContent();
} public void ReportHeader()
{
Console.WriteLine("This is report header3.");
}
} #endregion
#region Footer1
public class Footer1 : ReportDecorator
{
public Footer1(Report myReport)
: base(myReport)
{
} public override void ReportContent()
{
base.ReportContent();
ReportFooter();
} public void ReportFooter()
{
Console.WriteLine("This is report Footer1.");
}
}
#endregion
#region Footer2 public class Footer2 : ReportDecorator
{
public Footer2(Report myReport)
: base(myReport)
{
} public override void ReportContent()
{
base.ReportContent();
ReportFooter();
} public void ReportFooter()
{
Console.WriteLine("This is report Footer2.");
}
} #endregion
#region Footer3 public class Footer3 : ReportDecorator
{
public Footer3(Report myReport)
: base(myReport)
{
} public override void ReportContent()
{
base.ReportContent();
ReportFooter();
} public void ReportFooter()
{
Console.WriteLine("This is report Footer3.");
}
} #endregion
}
下面是客户端的调用代码,你需要怎么组合在你调用的时候就怎么组合。
Content clientReport = new Content();
Report header2 = new Header2(clientReport);
Report footer1 = new Footer1(header2);
footer1.ReportContent();
欢迎各位网友拍砖,本人也在不断学习中。。。
Decorator Pattern(装饰模式)的更多相关文章
- 第 13 章 装饰模式【Decorator Pattern】
以下内容出自:<<24种设计模式介绍与6大设计原则>> Ladies and gentlemen,May I get your attention,Please?,Now I’ ...
- 装饰模式(Decorator pattern)
装饰模式(Decorator pattern): 又名包装模式(Wrapper pattern), 它以对客户端透明的方式扩展对象的功能,是继承关系的一个替代方案. 装饰模式以对客户透明的方式动态的给 ...
- 深入浅出设计模式——装饰模式(Decorator Pattern)
模式动机 一般有两种方式可以实现给一个类或对象增加行为: 继承机制,使用继承机制是给现有类添加功能的一种有效途径,通过继承一个现有类可以使得子类在拥有自身方法的同时还拥有父类的方法.但是这种方法是静 ...
- 二十四种设计模式:装饰模式(Decorator Pattern)
装饰模式(Decorator Pattern) 介绍动态地给一个对象添加一些额外的职责.就扩展功能而言,它比生成子类方式更为灵活.示例有一个Message实体类,某个对象对它的操作有Insert()和 ...
- .NET设计模式(10):装饰模式(Decorator Pattern)
.NET设计模式(10):装饰模式(Decorator Pattern) 装饰模式(Decorator Pattern) --.NET设计模式系列之十 年月..在....对于..由于使用装饰模 ...
- 乐在其中设计模式(C#) - 装饰模式(Decorator Pattern)
原文:乐在其中设计模式(C#) - 装饰模式(Decorator Pattern) [索引页][源码下载] 乐在其中设计模式(C#) - 装饰模式(Decorator Pattern) 作者:weba ...
- 第8章 装饰模式(Decorator Pattern)
原文 第8章 装饰模式(Decorator Pattern) 概述: 装饰模式是在不必改变原类文件和使用继承的情况下,动态地扩展一个对象的功能.它是通过创建一个包装对象,也就是装饰来包裹真实的对象. ...
- 设计模式系列之装饰模式(Decorator Pattern)
装饰器模式(Decorator Pattern)允许向一个现有的对象添加新的功能,同时又不改变其结构.这种类型的设计模式属于结构型模式,它是作为现有的类的一个包装.这种模式创建了一个装饰类,用来包装原 ...
- C#设计模式之八装饰模式(Decorator Pattern)【结构型】
一.引言 今天我们要讲[结构型]设计模式的第三个模式,该模式是[装饰模式],英文名称:Decorator Pattern.我第一次看到这个名称想到的是另外一个词语“装修”,我就说说我对“装修”的理解吧 ...
随机推荐
- IE8,9下的ajax缓存问题
最近在做一个网站的登录注册框,前端使用了jquery.由于sign和login不是在单独的页面上,而是以一个弹出框出现.所以决定使用ajax来实现注册和登录功能.本以为可以一帆风顺,结果在测试的时候发 ...
- php以fastCGI的方式运行在iis下,遇到的文件系统权限问题及解决方法
今天准备将一个php demo放在IIS下运行,网站在IIS下的配置是这样的: 应用程序池是集成模式下的.net framework 2.0(2.0或4.0没什么关系,因为php以fastCGI的方式 ...
- GDI泄露检测
前一段在一个仿QQ的IM通讯工具中加入屏幕截图以及截图编辑功能,但是测试中发现当连续进行几十次截图后,系统会出现白屏,开始以为和win7经常闪白有关,屏幕截图截取到闪白的瞬间导致白屏,后来发现是GDI ...
- 一步一步学android之布局管理器——LinearLayout
线性布局是最基本的一种布局,在基本控件篇幅中用到的都是LinearLayout,线性布局有两种方式,前面也有用到,一种是垂直的(vertical),一种是水平的(horizontal).我们同样来看下 ...
- 如何使用ssh-keygen生成key
ssh-keygen - 生成.管理和转换认证密钥 通常使用:[b]ssh-keygen -i -f 公密匙名>> authorized_keys[/b] 语法详细介绍 [code]ssh ...
- 假设给Contact的List加一个用字母排序的导航
效果图: 这样写Layout: <? xml version="1.0" encoding="utf-8"? > <LinearLayout ...
- 自己定义控件-GifView
一.描写叙述 显示Gif 的View 原理是用 MediaPlayer 实现的 二.源代码 https://github.com/mentor811/Demo_GifView [ 声明:版权全部,欢迎 ...
- mvc 防止客服端多次提交
但凡web开发中都会有户多次点击了提交按钮导致多次提交的情况,一般的集中做法 1.通过js在用户点击的时候将按钮disabled掉,但是这样并不是很可靠(我就可以跳过这个,用一个for循环 我直接自己 ...
- TabelView的多选模式
@interface ViewController ()<UITableViewDelegate,UITableViewDataSource> @property(nonatomic,st ...
- HDOJ 1166.敌兵布阵
2015-06-08 问题简述: 原题的题意相当于有一些连续摆放的箱子,里面装着球,球的数量可以加减,现要查询几个连续的箱子里球的总数,其中存在放球和拿球的操作. 原题链接:http://acm.hd ...