OOAD(面向对象分析和设计)GRASP之创建者模式(Creator)又称生成器模式学习笔记
说OOAD是一门玄学,一点都不为过。又或许是因为我之前一直没有很好的建立面向对象的思想,更有可能是因为练得不够多。。。总之,一直没能很好理解,哪怕把一本叫做《UML和模式应用》的书翻来覆去好多遍还是没懂。这种感觉吧,像是把一个很难咀嚼的东西硬是吞了下去,刺激胃产生了强烈反应,可惜一堆胃酸还是没能把这东西溶解,反倒是喝了肌酸的感觉。但是,喜大普奔的是,就在刚才,我终于觉得我好像顿悟了些什么。顺便《大话设计模式》是一本好书!浅显易懂。
————————————————————————————————————————————————————————————————
创建者模式,顾名思义,先问一个问题:谁创建了对象X?
书上说:你可以依靠LRG(低表示差异),来从领域模型中获得灵感。
可惜我没太搞懂LRG和领域模型的精髓,所以这句话对我来说是废话。
——————————————————————————————————
那么我们不防先把此模式的角色拎出来:
大致有四种角色:
建造者(Builder):只是指明抽象接口
具体建造者(ConcreteBuilder):用来实现Builder的接口以构造和装配该产品的各个部件
指挥者(Director):指挥(如何造)并构造一个使用Builder接口的对象
产品(Product):表示被构造的复杂对象。理解成一些小零件
把四种角色区分好之后,我们就可以分别定义它们,以及它们之间的关系(这里,我们以上帝创造了人来举例):
建造者(Builder),即上帝,上帝创建了人。那为了创建人,上帝要怎么做?这个怎么做,即builder这个类的方法。人有四肢,所以上帝要先创建头(head)、躯干(body)、手(arm)、腿(leg)。另外,职责驱动设计,上帝的职责最后是要创建一个人出来的,所以builder还要通过协作来创建人(person)这个对象,需要makeperson这个方法。于是,创建者的类就被我们画了出来。
具体建造者(ConcreteBuilder),即具体的人(person),人分胖(FatBuilderPerson)、瘦(SilmBuilderPerson)、美(BeautyBuilderPerson)、丑(UglyBuilderPerson),具体创建者应该继承自创造者(builder),因为不论是胖瘦美丑,都是一个人,都拥有四肢。如此,具体建造者(Concretebuilder)的类我们也画出来了。
指挥者(Director),指挥者是指挥如何把四肢这些部位并在一起,成为真正的人的。所以指挥者需要有一个buildperson的方法。那么指挥者的类也画出来了。
产品(Product),顾名思义,就是一些部件了,在这个例子中,所谓产品具体就是指人的四肢。那么产品这个类也出来了。
知道它们的意义和相互之间的关系,我们可以画出此模式的完整类图啦。

那么相应的代码实现也就简单啦:
// 要建造的产品
public class Person
{
public string Head { get; set; }
public string Body { get; set; }
public string Arm { get; set; }
public string Leg { get; set; }
} // 定义创建者接口,实现者必须实现该接口中定义的所有抽象方法,防止实现者疏忽而遗漏某个部件的创建
public abstract class Builder
{
protected Person Person { get; set; }
public Builder()
{
Person = new Person();
} // 建造头
public abstract void BuildHead();
// 建造身体
public abstract void BuildBody();
// 建造胳膊
public abstract void BuildArm();
// 建造腿
public abstract void BuildLeg(); // 返回生成好的对象,这是一个具体方法,每个子类都可以使用它来返回一个已经创建成功的对象
public Person MakePerson()
{
return Person;
}
} // 建造者的具体实现,这里是要建造出一个瘦子
public class SilmPersonBuilder : Builder
{
public SilmPersonBuilder()
{
Person = new Person();
} public override void BuildHead()
{
Person.Head = "瘦子的脑袋";
} public override void BuildBody()
{
Person.Body = "瘦子的身体";
} public override void BuildArm()
{
Person.Arm = "瘦子的胳膊";
} public override void BuildLeg()
{
Person.Leg = "瘦子的腿";
} } // 建造者的具体实现,这里是要建造出一个胖子
public class FatPersonBuilder : Builder
{
public override void BuildHead()
{
Person.Head = "胖子的脑袋";
} public override void BuildBody()
{
Person.Body = "胖子的身体";
} public override void BuildArm()
{
Person.Head = "胖子的胳膊";
} public override void BuildLeg()
{
Person.Head = "胖子的腿";
}
} // 建造者模式中的指挥者
public class PersonDirector
{
Builder builder;
public PersonDirictor(Builder personBuilder)
{
builder = personBuilder;
} // 指挥创建一个人的过程,并返回创建成功的产品
public Person BuildPerson()
{
builder.BuildHead();
builder.BuildBody();
builder.BuildArm();
builder.BuildLeg(); return builder.MakePerson();
}
}
创建者模式(Creator)的意义和优点:能够将复杂对象的构建和它的表示分离,使同样的构建过程,可以创造不同的表示。对于用户来说,只要给定建造类型不需要知道具体建造过程和细节了。但缺点是内部细节不容易修改。
以上,如有不足请多多指正!
OOAD(面向对象分析和设计)GRASP之创建者模式(Creator)又称生成器模式学习笔记的更多相关文章
- UML和模式应用学习笔记-1(面向对象分析和设计)
UML和模式应用学习笔记-1(面向对象分析和设计) 而只是对情节的记录:此处的用例场景为:游戏者请求掷骰子.系统展示结果:如果骰子的总点数是7,则游戏者赢得游戏,否则为输 (2)定义领域模型:在领域模 ...
- 《UML和模式应用》读书笔记(一)面向对象分析和设计简单示例
在开始进行对象分析和设计之前,先通过“扔骰子”这个软件(游戏者扔两个骰子,如果总是是7,则赢,否则输),来简单分析下这个过程. 1:用例 需求分析,可能包括人们如何应用的场景或情节,这些都可以被编写成 ...
- 解析UML的面向对象分析与设计
经常听到有朋友抱怨,说学了UML不知该怎么用,或者画了UML却觉得没什么作用.其实,就UML本身来说,它只是一种交流工具,它作为一种标准化交流符号,在OOA&D过程中开发人员间甚至开发人员与客 ...
- .NET应用架构设计—面向对象分析与设计四色原型模式(彩色建模、领域无关模型)(概念版)
阅读目录: 1.背景介绍 2.问自己,UML对你来说有意义吗?它帮助过你对系统进行分析.建模吗? 3.一直以来其实我们被一个缝隙隔开了,使我们对OOAD遥不可及 4.四色原型模式填补这个历史缝隙,让我 ...
- 面向对象分析与设计—OOD部分
第三部分 面向对象设计 3.1 面向对象设计(OOD)的定义? 在面向对象分析阶段,已经针对用户需求建立起用面向对象概念描述的系统分析模型.在设计阶段,要考虑为实现系统而采用的计算机设备.操作系统.网 ...
- 面向对象分析与设计—OOA部分
第二部分 面向对象分析 2.1 面向对象分析(OOA)的定义? OOA——面向对象的分析,就是运用面向对象方法进行系统分析,对问题域(问题所涉及的范围)和系统责任(所开发的系统应具备的职能)进行分析与 ...
- 《Linux内核设计与实现》课本第一章&第二章学习笔记
<Linux内核设计与实现>课本学习笔记 By20135203齐岳 一.Linux内核简介 Unix内核的特点 Unix很简洁,所提供的系统调用都有很明确的设计目的. Unix中一切皆文件 ...
- 基于UML的面向对象分析与设计
前言 经常听到有朋友抱怨,说学了UML不知该怎么用,或者画了UML却觉得没什么作用.其实,就UML本身来说,它只是一种交流工具,它作为一种标准化交流符号,在OOA&D过程 ...
- 面向对象分析和设计(OOA/D)
UML不是OOA/D,也不是方法,它仅仅是一种图形表示法(表示的是OOA/D的想法),我们将在OOA/D中应用UML:分析,就是理解客户脑子中的概念,跟客户来沟通,分析出专业术语:设计,对分析出来的专 ...
随机推荐
- JS获取标签方法及兼容处理
document.getElementById('Id名'); // 所有浏览器 document.getElementsByTagName('标签名'); // 所有浏览器 document.ge ...
- SQLServer 2005 数据库定阅复制实现双机热备(主要是sharepoint 内容数据库)
原文:SQLServer 2005 数据库定阅复制实现双机热备(主要是sharepoint 内容数据库) 场景 公司最近的sharepoint的数据库服务器老是出问题,并且在一旦出现问题,就导致无法正 ...
- Linux:最终用途cat命令查看不可见的字符
常,的程序或软件,并没有语法错误,你检查其内容没有发现相关问题.这是时间,因为你用普通的文本编辑软件来查看,有很多的字符显示不出来的,但在最终用途cat命令可以很easy地检測出是否存在这些字符. ~ ...
- C# 笔试题,看你会几道题
1. Which interface you need to implement to support for each? IEnumerator IEnumerable ICompare ...
- CodeSmith
完美解决CodeSmith无法获取MySQL表及列Description说明注释的方案 问题描述: CodeSmith是现在比较实用的代码生成器,但是我们发现一个问题: 使用CodeSmith编写 ...
- 快速构建Windows 8风格应用31-构建磁贴
原文:快速构建Windows 8风格应用31-构建磁贴 引言 磁贴是吸引用户经常使用应用重要手段之一.我们可将应用程序内较好的内容使用磁贴进行展示. 另外应用程序磁贴是应用程序中的核心部分,而且很可能 ...
- Mybatis之动态构建SQL语句
今天一个新同事问我,我知道如何利用XML的方式来构建动态SQL,可是Mybatis是否能够利用注解完成动态SQL的构建呢?!!答案是肯定的,MyBatis 提供了注解,@InsertProvider, ...
- Mac OSX系统安装和配置Zend Server 6教程(2)
继上一节安装好Zend Server 6以后,我们需要修改配置文件.首先修改服务器监听端口.默认的情况下Zend Server 6安装以后的端口是10088.一般开发者使用的都是HTTP默认端口80. ...
- Libgdx Box2D现实---这缓释微丸(两:Box2D介绍)
Box2D官方网站 : http://box2d.org/ Box2D v2.1.0用户手冊翻译 : http://blog.csdn.net/complex_ok/article/catego ...
- java在string和int相互转化
1 如何串 String 转换成整数 int? A. 有两种方法: 1). int i = Integer.parseInt([String]); 或 i = Integer.parseInt([St ...