深入解析Python设计模式编程中建造者模式的使用


Posted in Python onMarch 02, 2016

建造者模式:将一个复杂对象的构建与他的表示分离,使得同样的构建过程可以创建不同的表示。

基本思想
某类产品的构建由很多复杂组件组成;
这些组件中的某些细节不同,构建出的产品表象会略有不同;
通过一个指挥者按照产品的创建步骤来一步步执行产品的创建;
当需要创建不同的产品时,只需要派生一个具体的建造者,重写相应的组件构建方法即可。

代码结构

class Builder(object):
  """基类"""
  def Part1(self):
    # 不同类型的产品,该步骤的细节可能不同
    raise NotImplementedError()

  def Part2(self):
    # 不同类型的产品,该步骤的细节可能不同
    raise NotImplementedError()

class Builder1(Builder):
  """派生类,生产builder1类型的产品"""
  def Part1(self):
    print 'builder1 Part1'

  def Part2(self):
    print 'builder1 Part2'

class Builder2(Builder):
  """派生类,生产builder2类型的产品"""
  def Part1(self):
    print 'builder2 Part1'

  def Part2(self):
    print 'builder2 Part2'

class Director(object):
  """指挥者,负责组织产品的构建过程"""
  def Build(self, builder):
    builder.Part1()
    builder.Part2()

def client():
  director = Director()
  director.Build(Builder1())
  director.Build(Builder2())

这里有一个疑问,指挥者这个角色有什么用呢。感觉除了增加client的调用负担外,似乎没什么用处。为什么不把产品构建过程放在Builder基类中呢,像下面这样:

class Builder(object):
  """基类"""
  def Part1(self):
    raise NotImplementedError()

  def Part2(self):
    raise NotImplementedError()

  def Build(self):
    self.Part1()
    self.Part2()

class Builder1(Builder):
  def Part1(self):
    print 'builder1 Part1'

  def Part2(self):
    print 'builder1 Part2'

class Builder2(Builder):
  def Part1(self):
    print 'builder2 Part1'

  def Part2(self):
    print 'builder2 Part2'

def client():
  Builder1().Build()
  Builder2().Build()

没错,上面就是典型的模板方法模式的实现套路,回顾一下模板方法模式的定义: > 模板方法模式:定义一个工作流或算法的基本骨架,而将一些特定步骤的实现延迟到子类中。

模板方法模式更多的关注于算法流程,而建造者模式更多的关注于复杂对象的创建,模板模式应用场景比建造者模式更多一些,写起来也更自然一些。

类图

深入解析Python设计模式编程中建造者模式的使用

实例

#encoding=utf-8 
# 
#by panda 
#建造者模式 
 
 
def printInfo(info): 
  print unicode(info, 'utf-8').encode('gbk') 
 
#建造者基类 
class PersonBuilder(): 
  def BuildHead(self): 
    pass 
   
  def BuildBody(self): 
    pass 
   
  def BuildArm(self): 
    pass 
 
  def BuildLeg(self): 
    pass 
   
#胖子 
class PersonFatBuilder(PersonBuilder): 
  type = '胖子' 
  def BuildHead(self): 
    printInfo("构建%s的头" % self.type) 
   
  def BuildBody(self): 
    printInfo("构建%s的身体" % self.type) 
   
  def BuildArm(self): 
    printInfo("构建%s的手" % self.type) 
 
  def BuildLeg(self): 
    printInfo("构建%s的脚" % self.type) 
   
 
#瘦子 
class PersonThinBuilder(PersonBuilder): 
  type = '瘦子' 
  def BuildHead(self): 
    printInfo("构建%s的头" % self.type) 
   
  def BuildBody(self): 
    printInfo("构建%s的身体" % self.type) 
   
  def BuildArm(self): 
    printInfo("构建%s的手" % self.type) 
 
  def BuildLeg(self): 
    printInfo("构建%s的脚" % self.type) 
 
#指挥者 
class PersonDirector(): 
  pb = None; 
  def __init__(self, pb): 
    self.pb = pb 
   
  def CreatePereson(self): 
    self.pb.BuildHead() 
    self.pb.BuildBody() 
    self.pb.BuildArm() 
    self.pb.BuildLeg() 
 
def clientUI(): 
  pb = PersonThinBuilder() 
  pd = PersonDirector(pb) 
  pd.CreatePereson() 
   
  pb = PersonFatBuilder() 
  pd = PersonDirector(pb) 
  pd.CreatePereson() 
  return 
 
 
if __name__ == '__main__': 
  clientUI();
Python 相关文章推荐
布同 统计英文单词的个数的python代码
Mar 13 Python
Python使用urllib模块的urlopen超时问题解决方法
Nov 08 Python
python 随机数使用方法,推导以及字符串,双色球小程序实例
Sep 12 Python
基于Python __dict__与dir()的区别详解
Oct 30 Python
python清理子进程机制剖析
Nov 23 Python
python 输出所有大小写字母的方法
Jan 02 Python
Flask框架模板继承实现方法分析
Jul 31 Python
python根据文本生成词云图代码实例
Nov 15 Python
OpenCV 之按位运算举例解析
Jun 19 Python
Django CBV模型源码运行流程详解
Aug 17 Python
Python3+RIDE+RobotFramework自动化测试框架搭建过程详解
Sep 23 Python
python3定位并识别图片验证码实现自动登录功能
Jan 29 Python
举例讲解Python设计模式编程中对抽象工厂模式的运用
Mar 02 #Python
实例讲解Python设计模式编程之工厂方法模式的使用
Mar 02 #Python
详解设计模式中的工厂方法模式在Python程序中的运用
Mar 02 #Python
探究python中open函数的使用
Mar 01 #Python
Saltstack快速入门简单汇总
Mar 01 #Python
通过Python使用saltstack生成服务器资产清单
Mar 01 #Python
Python解析json文件相关知识学习
Mar 01 #Python
You might like
咖啡与水的关系
2021/03/03 冲泡冲煮
我的论坛源代码(八)
2006/10/09 PHP
php 执行系统命令的方法
2009/07/07 PHP
destoon实现调用热门关键字的方法
2014/07/15 PHP
php通过sort()函数给数组排序的方法
2015/03/18 PHP
php将HTML表格每行每列转为数组实现采集表格数据的方法
2015/04/03 PHP
PHP生成二维码与识别二维码的方法详解【附源码下载】
2019/03/07 PHP
php使用lua+redis实现限流,计数器模式,令牌桶模式
2019/04/04 PHP
js获取键盘按键响应事件(兼容各浏览器)
2013/05/16 Javascript
div模拟选择框示例代码
2013/11/03 Javascript
原生JS和jQuery版实现文件上传功能
2016/04/18 Javascript
使用jQuery给input标签设置默认值
2016/06/20 Javascript
详解mpvue中使用vant时需要注意的onChange事件的坑
2019/05/16 Javascript
vue使用高德地图根据坐标定位点的实现代码
2019/08/22 Javascript
跟老齐学Python之让人欢喜让人忧的迭代
2014/10/02 Python
在win和Linux系统中python命令行运行的不同
2016/07/03 Python
Django中针对基于类的视图添加csrf_exempt实例代码
2018/02/11 Python
Python中new方法的详解
2019/01/15 Python
python 判断矩阵中每行非零个数的方法
2019/01/26 Python
Python3实现定时任务的四种方式
2019/06/03 Python
pytorch梯度剪裁方式
2020/02/04 Python
python轮询机制控制led实例
2020/05/03 Python
宝塔面板成功部署Django项目流程(图文)
2020/06/22 Python
如何利用python进行时间序列分析
2020/08/04 Python
Python 生成短8位唯一id实战教程
2021/01/13 Python
const char*, char const*, char*const的区别是什么
2014/07/09 面试题
自我评价中英文语句
2013/11/30 职场文书
优秀班主任经验交流材料
2014/06/02 职场文书
电子商务优秀毕业生求职信
2014/07/11 职场文书
群众路线四风自我剖析材料
2014/10/08 职场文书
个人总结格式范文
2015/03/09 职场文书
中秋联欢会主持词
2015/07/04 职场文书
社区安全温馨提示语
2015/07/14 职场文书
使用pytorch实现线性回归
2021/04/11 Python
一文弄懂MySQL中redo log与binlog的区别
2022/02/15 MySQL
漫画《催眠麦克风-Dawn Of Divisions》第二卷PV公开
2022/04/05 日漫