王朝网络
分享
 
 
 

Python设计模式——用模式改善软件设计

王朝other·作者佚名  2008-05-19
宽屏版  字体: |||超大  

一、什么是设计模式

设计模式(design pattern)的提出,是面向对象程序设计演化过程中的一个重要里程碑。正如Gamma,Helm,Johnson和Vlissides在他们的经典著作《设计模式》一书中所说的:设计模式使得人们可以更加简单和方便地去复用成功的软件设计和体系结构,从而能够帮助设计者更快更好地完成系统设计。

设计模式的概念最早起源于建筑设计大师Christopher Alexander关于城市规划和建筑设计的著作《建筑的永恒方法》,尽管Alexander的著作是针对建筑领域的,但他的观点实际上适用于所有的工程设计领域,其中就包括软件设计领域。在《建筑的永恒方法》一书中,Alexander是这样描述模式的:

模式是一条由三部分组成的规则,它表示了一个特定环境、一个问题和一个解决方案之间的关系。每一个模式描述了一个在我们周围不断重复发生的问题,以及该问题的解决方案的核心。这样,你就能一次又一次地使用该方案而不必做重复劳动。

将设计模式引入软件设计和开发过程的目的在于充分利用已有的软件开发经验,这是因为设计模式通常是对于某一类软件设计问题的可重用的解决方案。优秀的软件设计师都非常清楚,不是所有的问题都需要从头开始解决,他们更愿意复用以前曾经使用过的解决方案,每当他们找到一个好的解决方案,他们会一遍又一遍地使用,这些经验是他们成为专家的部分原因。设计模式的最终目标就是帮助人们利用熟练的软件设计师的集体经验,来设计出更加优秀的软件。

在软件设计领域中,每一个设计模式都系统地命名、解释和评价了面向对象系统中的一个重要的和可复用的设计。这样,我们只要搞清楚这些设计模式,就可以完全或者说很大程度上吸收了那些蕴含在模式中的宝贵经验,从而对软件体系结构有了比较全面的了解。更加重要的是,这些模式都可以直接用来指导面向对象系统设计中至关重要的对象建模问题,实际工作中一旦遇到具有相同背景的场合,只需要简单地套用这些模式就可以了,从而省去了很多摸索工作。

二、经典的设计模式MVC

在长期的软件实践过程中,人们逐渐总结出了一些实用的设计模式,并将它们应用于具体的软件系统中,出色地解决了很多设计上的难题。源于Smalltalk,并在Java中得到广泛应用的模型-视图-控制器(Model-View-Controller,MVC)模式,是非常经典的一个设计模式,通过它你可以更好地理解"模式"这一概念。

MVC模式通常用在开发人机交互软件的时候,这类软件的最大特点就是用户界面容易改变,例如,当你要扩展一个应用程序的功能时,通常需要修改菜单来反映这种变化。如果用户界面和核心功能紧紧交织在一起,要建立这样一个灵活的系统通常是非常困难的,因为很容易产生错误。为了更好地开发这样的软件系统,系统设计师必须考虑下面两个因素:

用户界面应该是易于改变的,甚至在运行期间也是有可能改变的;

用户界面的修改或移植不会影响软件的核心功能代码。

为了解决这个问题,可以采用将模型(Model)、视图(View)和控制器(Controller)相分离的思想。在这种设计模式中,模型用来封装核心数据和功能,它独立于特定的输出表示和输入行为,是执行某些任务的代码,至于这些任务以什么形式显示给用户,并不是模型所关注的问题。模型只有纯粹的功能性接口,也就是一系列的公开方法,这些方法有的是取值方法,让系统其它部分可以得到模型的内部状态,有的则是置值方法,允许系统的其它部分修改模型的内部状态。

视图用来向用户显示信息,它获得来自模型的数据,决定模型以什么样的方式展示给用户。同一个模型可以对应于多个视图,这样对于视图而言,模型就是可重用的代码。一般来说,模型内部必须保留所有对应视图的相关信息,以便在模型的状态发生改变时,可以通知所有的视图进行更新。

控制器是和视图联合使用的,它捕捉鼠标移动、鼠标点击和键盘输入等事件,将其转化成服务请求,然后再传给模型或者视图。整个软件的用户是通过控制器来与系统交互的,他通过控制器来操纵模型,从而向模型传递数据,改变模型的状态,并最后导致视图的更新。

MVC设计模式将模型、视图与控制器三个相对独立的部分分隔开来,这样可以改变软件的一个子系统而不至于对其它子系统产生重要影响。例如,在将一个非图形化用户界面软件修改为图形化用户界面软件时,不需要对模型进行修改,而添加一个对新的输入设备的支持,则通常不会对视图产生任何影响。

应用了MVC设计模式的软件系统,其基本的实现过程是:

控制器创建模型;

控制器创建一个或多个视图,并将它们与模型相关联;

控制器负责改变模型的状态;

当模型的状态发生改变时,模型会通知与之相关的视图进行更新。

如果用UML来表示MVC设计模式,则如图1所示:

三、Python与设计模式

尽管设计模式的目标是努力做到与语言的无关性,但事实上许多模式在应用时还是需要依赖于具体实现语言的某些特性,尤其是该语言的对象模型。由于《设计模式》一书采用的是C++和Smalltalk来讲述设计模式,因此访问控制符和静态成员方法(类方法)等都可以直接使用,可惜的是这些特性在Python中都无法用到,原因是Python采了与C++完全不同的对象模式。

简单说来,Python是一种优秀的面向对象脚本语言,它具有动态语义和快速的原型开发能力,也许在短短的几分钟内,你就可以开发出使用其它语言可能需要花费几个小时的原型系统。Python丰富的工具集使得它位于传统脚本语言(如Tcl、Perl和Scheme)和系统编程语言(如C、C++和Java)之间,既具备了脚本语言的简单易用性,同时又能够提供只有系统语言才可能拥有的某些高级特性。

从面向对象角度来看,Python和Smalltalk一样都采用了完全的面向对象设计思想,其对象模型能够支持诸如运算符重载、多重继承等高级概念。但Python在设计时似乎忽略了面向对象的一项基本原则,那就是数据隐藏。与C++和Java不同,Python没有为类定义提供public、protected和private等关键字,这就意味着任何人都可以直接修改对象的属性。Python之所以这么做,也许是为了保证语法上的简洁性,就像Python的发明人Guido van Rossum所认为的那样:"丰富的语法带来的负担多于帮助"。但在某些设计模式中,向外界隐藏数据和方法都是非常必要的,为此我们不得不利用Python对象模型提供的某些高级特性,来实现某种程度上的隐藏性。

在Python中应用设计模式的一个有利因素是它的动态类型绑定,也就是说一个对象很少只是一个类的实例,而是可以在运行时动态改变。在面向对象系统中,接口是一个基本的组成部分,对象只有通过它们的接口才能与外界进行交互。对象的接口与其功能是完全分离的,支持相同请求的不同对象针对同一请求所触发的操作可能完全不同,这就是动态绑定的概念。动态绑定虽然看起来在一定程度上使得代码不同那么容易理解和维护,但它的确可以使整个软件系统的结构显得更加清晰和合理。

作为一门优秀的脚本语言,Python正在被越来越多的人所接受,使用Python开发的项目也越来越多,这也难怪会被大家推崇为"下一代编程语言"中的典型代表。随着应用范围的不断扩展,如何在用Python开发软件时充分利用已有的经验和成果将成为人们关注的焦点,而设计模式作为软件复用的一个重要方面,其价值自然是不言而喻。可问题是目前所使用的设计模式大都是人们在用Smalltalk、C++和Java开发软件时所总结出来的,因此或多或少地带有这些语言的影子,而要想在Python中使用这些设计模式,必须根据Python的自身特点和实际需要,灵活地加以运用。

四、Python对象模型

对一门具体的编程语言来说,在应用设计模式时影响最大的莫过于它的对象模型了,这是因为大部分设计模式都源自于C++和Java这类面向对象编程语言。要想在Python中复用这些设计模式,首先需要对Python的对象模型有一个比较清晰的认识。

4.1 类

同其它面向对象编程语言一样,Python中的类也是一种用户自定义的数据类型,其基本的语法格式是:

class (superclass, ...):# 定义类

data = value# 共享的类变量

def method(self, ...):# 类中的方法

self.member = value# 实例的数据

类定义从关键字class开始,并包含整个缩进代码块,类中定义的方法和属性构成了类的名字空间(name space)。一个类通常会有多个方法,它们都以关键字def开头,并且第一个参数通常都是self,Python中的变量self相当于C++中的关键字this,其作用是传递一个对象的引用。

Python中的类属性位于类的名字空间中,可以被所有的类实例所共享,这一点同C++和Java相同。访问类属性时不需要事先创建类的实例,直接使用类名就可以了。例如:

class Friend:

default_age = 20

Friend.default_age

20

除了自定义的类属性外,Python中的每个类其实都具有一些特殊的类属性,它们都是由Python的对象模型所提供的。表1列出了这些类属性:

表1特殊的类属性

4.2 实例

定义类的目的是为了创建它的实例,从面向对象的角度看,类是对数据及其相关操作的封装,而类实例则是对现实生活中某个实体的抽象。假设定义了如下一个类:

class School:

 
 
 
免责声明:本文为网络用户发布,其观点仅代表作者个人观点,与本站无关,本站仅提供信息存储服务。文中陈述内容未经本站证实,其真实性、完整性、及时性本站不作任何保证或承诺,请读者仅作参考,并请自行核实相关内容。
2023年上半年GDP全球前十五强
 百态   2023-10-24
美众议院议长启动对拜登的弹劾调查
 百态   2023-09-13
上海、济南、武汉等多地出现不明坠落物
 探索   2023-09-06
印度或要将国名改为“巴拉特”
 百态   2023-09-06
男子为女友送行,买票不登机被捕
 百态   2023-08-20
手机地震预警功能怎么开?
 干货   2023-08-06
女子4年卖2套房花700多万做美容:不但没变美脸,面部还出现变形
 百态   2023-08-04
住户一楼被水淹 还冲来8头猪
 百态   2023-07-31
女子体内爬出大量瓜子状活虫
 百态   2023-07-25
地球连续35年收到神秘规律性信号,网友:不要回答!
 探索   2023-07-21
全球镓价格本周大涨27%
 探索   2023-07-09
钱都流向了那些不缺钱的人,苦都留给了能吃苦的人
 探索   2023-07-02
倩女手游刀客魅者强控制(强混乱强眩晕强睡眠)和对应控制抗性的关系
 百态   2020-08-20
美国5月9日最新疫情:美国确诊人数突破131万
 百态   2020-05-09
荷兰政府宣布将集体辞职
 干货   2020-04-30
倩女幽魂手游师徒任务情义春秋猜成语答案逍遥观:鹏程万里
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案神机营:射石饮羽
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案昆仑山:拔刀相助
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案天工阁:鬼斧神工
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案丝路古道:单枪匹马
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案镇郊荒野:与虎谋皮
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案镇郊荒野:李代桃僵
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案镇郊荒野:指鹿为马
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案金陵:小鸟依人
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案金陵:千金买邻
 干货   2019-11-12
 
>>返回首页<<
推荐阅读
 
 
频道精选
 
静静地坐在废墟上,四周的荒凉一望无际,忽然觉得,凄凉也很美
© 2005- 王朝网络 版权所有