本文发表在作者José M. Aguilar的博客Variable Not Found,后来由Timm Martin翻译成英文发表在DevTopics上。我在真见的blog那里看到,将其翻译过来share给大家,共同学习。有翻译不当之处,望大侠斧正。
以下是如何注释代码的13tips,它们会在日后帮助你更容易理解和维护代码。
1. Comment each level(每个级别的注释有统一的风格)
注释每一个代码块,并且在各个级别的代码块上,要使用统一的注释方法。例如:
- 对于类,应包含简单的描述、作者以及最近的更改日期
- 对于方法,应包含目的的描述、功能、参数以及返回值
使用统一的注释规则对于一个团队是非常重要的。当然,更加推荐使用注释的约定和工具(例如,C#的XML或Java的Javadoc),它们会是注释变得更加容易。
2. Use paragraph comments(对段落注释)
将代码块分成若干完成独立功能的“段落”,并在每个“段落”前添加注释,向读者说明“即将发生什么”。
// Check that all data records
// are correct
foreach (Record record in records)
{
if (rec.checkStatus()==Status.OK)
{
. . .
}
}
// Now we begin to perform
// transactions
Context ctx = new ApplicationContext();
ctx.BeginTransaction();
. . .
3. Align comments in consecutive lines(对齐注释行)
对于拥有后缀式注释的多行代码,排版注释代码,使各行注释对齐到同一列。
const MAX_ITEMS = 10; // maximum number of packets
const MASK = 0x1F; // mask bit TCP
一些开发人员使用tab来对齐注释,有些则使用空格。但是由于tab在不同的编辑器或者IDE上会有所不同,最好还是使用空格。
4. Don't insult the reader's intelligence(不要侮辱读者的智商)
不要写没用的注释,例如:
if (a == 5) // if a equals 5
counter = 0; // set the counter to zero
写这种无用的注释不但浪费你的时间,而且读者在读这种很容易理解的代码时,很容易被你的注释转移注意力,浪费了时间。
5. Be polite(要有礼貌)
不要写不礼貌的注释代码,例如“注意,愚蠢的使用者输入了一个负数”,或者“修正由于最初的开发者的可怜且愚蠢的编码所造成的副作用”。这样的注释冒犯了作者,而且你并不知道谁会在将来读到这段注释——你老板、客户或者是你在注释中冒犯的那个可怜且愚蠢的开发人员。
6. Get to the point(简明扼要)
不要在注释中写的过多,不要写玩笑、诗和冗长的话。总之,注释需要简单直接。
7. Use a consistent style(风格一致)
一些人认为注释应该能让非程序员也能看懂,但是也有些人认为注释仅仅是指导程序员的。不管怎么说,像《Successful Strategies for Commenting Code》中所说,真正重要的是注释始终面向同一个读者,在这点上,应该保持一致。个人认为,我很怀疑会有非程序人员阅读代码,所以应该把阅读注释的对象定位为开发人员。
8. Use special tags for internal use(在内部使用特殊的标签)
团队中处理代码时,在程序员之间应采用一系列统一的‘标签注释’进行交流。例如,很多团队使用“TODO”来表示一段需要额外工作的代码。
int Estimate(int x, int y)
{
// TODO: implement the calculations
return 0;
}
‘标签注释’并不解释代码,而是引起主意或者传递信息。但是,使用这种方法时,务必要完成‘标签注释’传递的信息。
9. Comment code while writing it(写代码的同时,完成注释)
写代码的同时添加注释,因为此时你的思路最为清晰。如果你把注释的任务留到最后,那么你相当于经历了两次编码。“我没有时间注释”“我太忙了”“项目耽误了”这些往往是不写注释的理由。所以,程序员们认为,最理想的解决方法是‘写代码前先写注释’。例如:
public void ProcessOrder()
{
// Make sure the products are available
// Check that the customer is valid
// Send the order to the store
// Generate bill
}
10. Write comments as if they were for you (in fact, they are)把代码的读者想象成你自己(实际情况往往如此)
注释代码时,不仅仅要为将来可能维护你代码的人考虑,而且要考虑到读注释的可能是你。伟大的Phil Haack说过:“每当有偶一行代码被敲上屏幕,你都要从维护的角度审视一边这段代码。” "As soon as a line of code is laid on the screen, you’re in maintenance mode on that piece of code."(著名的话不敢不附上原句)
结果,我们自己往往是我们良好注释的受益者,或者是烂注释的受害人。
11. Update comments when you update the code(更新代码时,记得更新注释)
如果不能随着代码的更新而更新注释,那么即使再准确的注释也毫无意义。代码和注释必须同步,否则这些注释对于维护你代码的程序人员来说简直是折磨。在使用refactoring工具自动更新代码时,应尤其注意,它们会自动更新代码而不会改变注释,这些注释自然就过期了。
12. The golden rule of comments: readable code(可读性良好的代码是最好的注释)
对于许多程序员来说,基本的原则之一就是:让代码自己说话。有人可能会怀疑这是那些不爱写注释的程序员的借口,然而这确实是一个不争的事实。自我解释良好的代码对于编码来说大有益处,不但代码容易理解甚至使注释变得没有必要。举例来说,在我的文章《Fluid Interfaces》中展示了什么是清晰的自我解释型代码:
Calculator calc = new Calculator();
calc.Set(0);
calc.Add(10);
calc.Multiply(2);
calc.Subtract(4);
Console.WriteLine( "Result: {0}", calc.Get() );
在本例中,注释是没必要的,并且会违背tip#4 。为了使代码更加可读,应该考虑使用适当的名字(像在经典的《Ottinger's Rules》描述的),确保正确的缩进和代码风格栏线(代码风格栏线是类似于#region #endregion这类的东西吧?)。如果这一点做的不好,直接后果是,你的注释看起来就像是在为晦涩难懂的代码而道歉。
13. Share these tips with your colleagues(与你的同事share这些tips)
尽管tip#10中曾说过良好的注释会是自己从中收益,但是这些tips会使所有开发人员收益,尤其是在团队合作的环境中。因此大方的与同事分享这些注释的技巧,让我们都能写出易懂而且好维护的代码。
http://www.cnblogs.com/Willson/archive/2008/07/23/1249805.html
表结构
-- Create table 源表
create table INPUT_FWMJ
(
JGBH CHAR(5) not null,
JGMC VARCHAR2(50) not null,
BMBH CHAR(10) not null,
BMMC VARCHAR2(50) not null,
FWMJ NUMBER(20,2) not null,
ZLBZ CHAR(1) not null
)
-- Create/Recreate primary, unique and foreign key constraints
alter table INPUT_FWMJ
add constraint 机构编号和部门编号 primary key (JGBH, BMBH)
--补录表
-- Create table
create table INPUT_FWMJ_CHANGE
(
TASKID NUMBER not null,
STATE VARCHAR2(100),
JGBHSOURCE CHAR(5),
BMBHSOURCE CHAR(10),
JGBH CHAR(5) not null,
JGMC VARCHAR2(50) not null,
BMBH CHAR(10) not null,
BMMC VARCHAR2(50) not null,
FWMJ NUMBER(20,2) not null,
ZLBZ CHAR(1) not null
)
-- Create/Recreate primary, unique and foreign key constraints
alter table INPUT_FWMJ_CHANGE
add constraint PK_INPUT_FWMJ_CHANGE primary key (JGBH, BMBH, TASKID)
--增加
insert
into input_fwmj(jgbh, jgmc, bmbh, bmmc, fwmj, zlbz)
select jgbh, jgmc, bmbh, bmmc, fwmj, zlbz
from input_FWMJ_change
where state = 'Added'
--删除
delete input_fwmj
where jgbh || bmbh in
(select JGBHSOURCE || BMBHSOURCE
from input_FWMJ_change
where input_FWMJ_change.State = 'Deleted')
--修改
update input_fwmj set
input_fwmj.fwmj =
(select input_FWMJ_change.fwmj
from input_FWMJ_change
where input_FWMJ_change.State = 'Updated'
and input_FWMJ_change.JGBHSOURCE =
input_fwmj.jgbh
and input_FWMJ_change.BMBHSOURCE =
input_fwmj.bmbh),
input_fwmj.zlbz =
(select input_FWMJ_change.zlbz
from input_FWMJ_change
where input_FWMJ_change.State = 'Updated'
and input_FWMJ_change.JGBHSOURCE =
input_fwmj.jgbh
and input_FWMJ_change.BMBHSOURCE =
input_fwmj.bmbh)
where exists((select 1
from input_FWMJ_change
where input_FWMJ_change.State = 'Updated'
and input_FWMJ_change.JGBHSOURCE =
input_fwmj.jgbh
and input_FWMJ_change.BMBHSOURCE =
input_fwmj.bmbh))
面向对象基本概念
乔高峰 于深圳整理(2007-01-13)
面向对象(object-oriented ;简称: OO)
至今还没有统一的概念,我这里把它定义为:按人们认识客观世界的系统思维方式,采用基于对象(实体)的概念建立模型,模拟客观世界分析、设计、实现软件的办法。通过面向对象的理念使计算机软件系统能与现实世界中的系统一一对应。
面向对象方法(Object-Oriented Method)是一种把面向对象的思想应用于软件开发过程中,指导开发活动的系统方法,简称OO (Object-Oriented)方法,是建立在“对象”概念基础上的方法学。对象是由数据和容许的操作组成的封装体,与客观实体有直接对应关系,一个对象类定义了具有相似性质的一组对象。而每继承性是对具有层次关系的类的属性和操作进行共享的一种方式。所谓面向对象就是基于对象概念,以对象为中心,以类和继承为构造机制,来认识、理解、刻画客观世界和设计、构建相应的软件系统。
面向对象方法作为一种新型的独具优越性的新方法正引起全世界越来越广泛的关注和高度的重视,它被誉为"研究高技术的好方法",更是当前计算机界关心的重点。十多年来,在对OO方法如火如荼的研究热潮中,许多专家和学者预言:正象70年代结构化方法对计算机技术应用所产生的巨大影响和促进那样,90年代OO方法会强烈地影响、推动和促进一系列高技术的发展和多学科的综合。
面向对象方法的由来与发展
回顾历史可激励现在,以规划将来。
OO方法起源于面向对象的编程语言(简称为OOPL)。50年代后期,在用FORTRAN语言编写大型程序时,常出现变量名在程序不同部分发生冲突的问题。鉴于此,ALGOL语言的设计者在ALGOL60中采用了以"Begin……End"为标识的程序块,使块内变量名是局部的,以避免它们与程序中块外的同名变量相冲突。这是编程语言中首次提供封装(保护)的尝试。此后程序块结构广泛用于高级语言如Pascal 、Ada、C之中。
60年代中后期,Simula语言在ALGOL基础上研制开发,它将ALGOL的块结构概念向前发展一步,提出了对象的概念,并使用了类,也支持类继承。70年代,Smalltalk语言诞生,它取Simula的类为核心概念,它的很多内容借鉴于Lisp语言。由Xerox公司经过对Smautalk72、76持续不断的研究和改进之后,于1980年推出商品化的,它在系统设计中强调对象概念的统一,引入对象、对象类、方法、实例等概念和术语,采用动态联编和单继承机制。
从80年代起,人们基于以往巳提出的有关信息隐蔽和抽象数据类型等概念,以及由Modula2、Ada和Smalltalk和等语言所奠定的基础,再加上客观需求的推动,进行了大量的理论研究和实践探索,不同类型的面向对象语言(如:Object-c、Eiffel、c++、Java、Object-Pascal等)逐步地发展和建立起较完整的和雨后春笋般研制开发出来,OO方法的概念理论体系和实用的软件系统。
面向对象源出于Simula,真正的OOP由Smalltalk奠基。Smalltalk现在被认为是最纯的OOPL。
正是通过Smalltalk80的研制与推广应用,使人们注意到OO方法所具有的模块化、信息封装与隐蔽、抽象性、继承性、多样性等独特之处,这些优异特性为研制大型软件、提高软件可靠性、可重用性、可扩充性和可维护性提供了有效的手段和途径。
80年代以来,人们将面向对象的基本概念和运行机制运用到其它领域,获得了一系列相应领域的面向对象的技术。面向对象方法已被广泛应用于程序设计语言、形式定义、设计方法学、操作系统、分布式系统、人工智能、实时系统、数据库、人机接口、计算机体系结构以及并发工程、综合集成工程等,在许多领域的应用都得到了很大的发展。1986年在美国举行了首届"面向对象编程、系统、语言和应用(OOPSLA'86)"国际会议,使面向对象受到世人瞩目,其后每年都举行一次,这进一步标志OO方法的研究已普及到全世界。
面向对象方法在80年代已经得到了很大的发展,并且已在计算机科学、信息科学、系统科学和产业界得到了有效的应用,显示出其强大的生命力。可以展望在90年代内,面向对象方法将会大更深、吏广、更高的方向上取得进展:
(1) 更深的方向:如OO方法的理论基础和形式化描述;用OO技术设计出新一代OS等。
(2) 更广的方向:如面向对象的知识表示;面向对象的仿真系统;面向对象的多媒体系统;面向对象的灵境系统等。
(3) 更高的方向:如从思维科学的高度来丰富OO方法学的本质属性,突破现有的面向对象技术的一些局限、研究统一的面向对象的范式等。
对象(object)
即指现实世界中各种各样的实体。它可以指具体的事物也可以指抽象的事物。如:整数1、2、3、流氓陈水扁、苹果、飞机、规则、法律、法规、表单等等。每个对象皆有自己的内部状态和运动规律,如流氓陈水扁具有名字、身高、体重等内部状态,具有吃饭、睡觉、打人、偷税、漏税等运动规律。在面向对象概念中我们把对象的内部状态称为属性、运动规律成为方法或事件。
对象是要研究的任何事物。从一本书到一家图书馆,单的整数到整数列庞大的数据库、极其复杂的自动化工厂、航天飞机都可看作对象,它不仅能表示有形的实体,也能表示无形的(抽象的)规则、计划或事件。对象由数据(描述事物的属性)和作用于数据的操作(体现事物的行为)构成一独立整体。从程序设计者来看,对象是一个程序模块,从用户来看,对象为他们提供所希望的行为。在对内的操作通常称为方法。
对象既可以是具体的物理实体的对象,也可以是人为的概念,或者是任何有明确边界和意义的东西。比如:一名员工、一家公司、贷款与借款等,都可以作为对象
类(class):
类是具有相似内部状态和运动规律的实体的集合(或统称、抽象)。类的概念来自于人们认识自然、认识社会的过程。在这一程中,人们主要使用两种方法:由特殊到一般的归纳法和由一般到特殊的演绎法。在归纳的过程中,我们从一个个具体的事物中把共同的特征抽取出来,形成一个一般的概念,这就是"归类";如:昆虫、狮子、爬行动物,因为它们都能动所以归类为动物。在演绎的过程中我们又把同类的事物,根据不同的特征分成不同的小类,这就是"分类";如动物->猫科动物->猫->大花猫等。对于一个具体的类,它有许多具体的个体,我们就管这些个体叫做"对象"。类的内部状态是指类集合中对象的共同状态;类的运动规律是指类集合中对象的共同运动规律。如:博拉图对人作如下定义:人是没有毛能直立行走的动物。在博拉图的定义中"人"是一个类,具有"没有毛、直立行走"等一些区别于其它事物的共同特征;而张三、李四、王五、流氓陈水扁等一个个具体的人,是"人"这个类的一个个"对象"。
类是对象的模板。即类是对一组有相同数据和相同操作的对象的定义,一个类所包含的方法和数据描述一组对象的共同属性和行为。类是在对象之上的抽象,对象则是类的具体化,是类的实例。类可有其子类,也可有其它类,形成类层次结构。
在面向对象的软件技术中,“类”就是对具有相同数据和相同操作的一组相似对象的定义。也就是说,类是对具有相同属性和行为的一个或多个对象的描述,通常在这种描述中也包括对怎样创建该类的新对象的说明。通俗的讲:类是对具有相同属性和行为的一组相似的对象的抽象。
方法:
方法就是对象所能执行的操作,也就是类中所定义的服务。方法描述了对象执行操作的算法,响应消息的方法。
属性:
属性是类中所定义的数据,它是对客观世界实休所具有的性质的抽象。类的每个实例都有自己特有的属性值。比如姓名、性别就可以作为员工的属性而出现。
Abstract Class:
抽象类,其不能用以创建对象实例,只能作为创建其子类的一个模板而存在。比如“线”是“直线”与“曲线”的抽象类。
类与类之间的关系:
依赖(Dependency):
两个事物间的语义关系,其中一个事物发生了变化会影响到另一个事物。
关联(Association):
是一种结构关系,它描述了一组链,链是对象之间的连接。比如一个人为一家公司工作(WorksFor),这里WorksFor就是一个关联。
链接(link):
是对象之间物理上或概念上的连接。例如:张三为微软公司工作(WorksFor),这里WorksFor就是一个链接。
聚合(Aggregation):
其是一种特殊形式的关联。表示整体与部分的关系。比如项目组与其各成员之间的关系就是一种聚合关系。
组合关系(Composition):
其也是一种特殊形式的关联。表示整体拥有各个部分,部分与整体共存。比如一个窗口是由文本框、列表框、菜单等组成的。关闭窗口,各个组成部分也相继消失,窗口与其各组成部分之间的关系便是组合关系。Ao对象中FeatureClass与Feature之间就是一种组合关系。
泛化(Generalization):
其是一种特殊/一般关系,特殊元素(子元素)/的对象可替代一般元素(父元素)的对象。也称为“Is a关系”。
实现(Realization):
是类元之间的语义关系,其中一个类元指定了由另一个类元保证执行的契约。
实例:
实例就是由某个特定的类所描述的一个具体的对象。比如汽车就是交通工具的一个实例。实际上类是建立对象时使用的“模板”,按照这个模板所建立的一个个具体的对象,就是类的实际例子,简称实例。
注意:当使用“对象”这个术语时,即可以指一个具体的对象,也可以泛指一般的对象,但是,当使用“实例”这个术语时,必然是指一个具体的对象。
消息(Message):
消息是指对象间相互联系和相互作用的方式。一个消息主要由5部分组成:发送消息的对象、接收消息的对象、消息传递办法、消息内容(参数)、反馈。
消息是对象之间进行通信的一种规格说明。一般它由三部分组成:接收消息的对象、消息名及实际变元。
类的特性:
类的定义决定了类具有以下5个特性:抽象、继承、封装、重载、多态。
抽象:
类的定义中明确指出类是一组具有内部状态和运动规律对象的抽象,抽象是一种从一般的观点看待事物的方法,它要求我们集中于事物的本质特征(内部状态和运动规律),而非具体细节或具体实现。面向对象鼓励我们用抽象的观点来看待现实世界,也就是说,现实世界是一组抽象的对象——类组成的。
继承:
继承是类不同抽象级别之间的关系。类的定义主要有2种办法归纳和演绎;由一些特殊类归纳出来的一般类称为这些特殊类的父类,特殊类称为一般类的子类,同样父类可演绎出子类; 父类是子类更高级别的抽象。子类可以继承父类的所有内部状态和运动规律。在计算机软件开发中采用继承性,提供了类的规范的等级结构;通过类的继承关系,使公共的特性能够共享,提高了软件的重用性。
继承性是子类自动共享父类之间数据和方法的机制。它由类的派生功能体现。一个类直接继职其它类的全部描述,同时可修改和扩充。继职具有传达室递性。继职分为单继承(一个子类只有一父类)和多重继承(一个类有多个父类)。类的对象是各自封闭的,如果没继承性机制,则类对象中数据、方法就会出现大量重复。继承不仅支持系统的可重用性,而且还促进系统的可扩充性。
广义地说,继承是指能够直接获得已有的性质与特征,而不必重复定义它们。在OO软件技术中,继承是子类自动地共享基类中定义的数据和方法的机制。继承性使得相似的对象可以共享程序代码和数据结构,从而大大减少了程序中的冗余信息。当允许一个类只能继承一个类时,类的继承就是单继承,比如C#语言中,一个类继承另一个类时只能是单继承,而C++语言中就允许一个类继承多个类。
封装:
对象间的相互联系和相互作用过程主要通过消息机制得以实现。对象之间并不需要过多的了解对方内部的具体状态或运动规律。面向对象的类是封装良好的模块,类定义将其说明(用户可见的外部接口)与实现(用户不可见的内部实现)显式地分开,其内部实现按其具体定义的作用域提供保护。类是封装的最基本单位。封装防止了程序相互依赖性而带来的变动影响。在类中定义的接收对方消息的方法称为类的接口。
封装是一种信息隐蔽技术,它体现于类的说明,是对象的重要特性。封装使数据和加工该数据的方法(函数)封装为一个整体,以实现独立性很强的模块,使得用户只能见到对象的外特性(对象能接受哪些消息,具有那些处理能力),而对象的内特性(保存内部状态的私有数据和实现加工能力的算法)对用户是隐蔽的。封装的目的在于把对象的设计者和对象者的使用分开,使用者不必知晓行为实现的细节,只须用设计者提供的消息来访问该对象。
所谓封装就是把某个事物包装起来,使外界不知道该事物的具体内容。其通过向外界提供接口的形式而存在。比如打开电视机,它提供的是一个打开/关闭按钮,其实际内容,究竟怎样让电视播放我们是不知道的。我们也不必关心那么多,我们只要知道通过这个动作能实现我们想要的功能就行了。通过封装,我们很好地实现了细节对外界的隐藏,从而达到数据说明与操作实现分离的目的,使用者只需要知道它的说明即可使用它。
多态(覆盖):
多态性是指同名的方法可在不同的类中具有不同的运动规律。在父类演绎为子类时,类的运动规律也同样可以演绎,演绎使子类的同名运动规律或运动形式更具体,甚至子类可以有不同于父类的运动规律或运动形式。不同的子类可以演绎出不同的运动规律。
对象根据所接收的消息而做出动作。同一消息为不同的对象接受时可产生完全不同的行动,这种现象称为多态性。利用多态性用户可发送一个通用的信息,而将所有的实现细节都留给接受消息的对象自行决定,如是,同一消息即可调用不同的方法。例如:Print消息被发送给一图或表时调用的打印方法与将同样的Print消息发送给一正文文件而调用的打印方法会完全不同。多态性的实现受到继承性的支持,利用类继承的层次关系,把具有通用功能的协议存放在类层次中尽可能高的地方,而将实现这一功能的不同方法置于较低层次,这样,在这些低层次上生成的对象就能给通用消息以不同的响应。在OOPL中可通过在派生类中重定义基类函数(定义为重载函数或虚函数)来实现多态性。
指子类对象可以像父类对象那样使用,同样的消息既可以发送给父类对象也可以发送给子类对象。也就是说,在父类与其子类之间共享一个行为的名字,但是却可以按各自的实际需要来加以实现。多态性机制不仅增加了面向对象软件系统的灵活性,进一步减少了信息的冗余。
重载:
重载指类的同名方法在给其传递不同的参数是可以有不同的运动规律。在对象间相互作用时,即使接收消息对象采用相同的接收办法,但消息内容的详细程度不同,接收消息对象内部的运动规律也可能不同。如图4,老板指派采购员买东西,当老板没有指明买什么时,采购员可能默认买地瓜;如老板指明要采购员买大米,采购员可能到最近的超市买10斤大米;如老板指明采购员今天晚上到福州东街口买5斤大米,那采购员将不得不按老板指定的时间、地点去购买5斤大米。
函数重载是指在同一作用域内的若干参数特征不同的函数可以使用的函数名字;运算符重载是指同一个运算符可以施加于不同类型的操作数上面。重载对于提高系统的灵活性和可读性起到了很好的作用。
包:
哲学认为现实世界中不同对象间的相互联系和相互作用构成了各种不同的系统,不同系统间的相互联系和相互作用构成了更庞大的系统,进而构成了整个世界。在面向对象概念中把这些系统称为包。
包的接口类:
在系统间相互作用时为了蕴藏系统内部的具体实现,系统通过设立接口界面类或对象来与其他系统进行交互;让其他系统只看到是这个接口界面类或对象,这个类在面向对象中称为接口类。
综上可知,在OO方法中,对象和传递消息分别表现事物及事物间相互联系的概念。类和继承是是适应人们一般思维方式的描述范式。方法是允许作用于该类对象上的各种操作。这种对象、类、消息和方法的程序设计范式的基本点在于对象的封装性和类的继承性。通过封装能将对象的定义和对象的实现分开,通过继承能体现类与类之间的关系,以及由此带来的动态联编和实体的多态性,从而构成了面向对象的基本特征。
面向对象的新方法论、新范型、新技术
OO方法的作用和意义决不只局限于编程技术,它是一种新的程序设计范型--面向对象程序设计范型;是信息系统开发的新方法论--面向对象方法学;是正在兴起的新技术--面向对象技术。
面向对象程序设计范型:程序设计范型(以下简称程设范型)具体指的是程序设计的体裁,正如文学上有小说、诗歌、散文等体裁,程序设计体裁是用程序设计语言表达各种概念和各种结构的一套设施。
目前,程设范型分为:过程式程设范型、函数式程设范型,此外还有进程式程设范型、事件程设范型和类型系统程设范型。每一程设范型都有多种程序设计语言支持(如:FORTRAN、PASCAL、C均体现过程式程设范型,用来进行面向过程的程序设计),而某些语言兼备多种范型(如:Lisp属过程与函数混合范型,C++则是进程与面向对象混合范型的语言)。
过程式程设范型是流行最广泛的程序设计范型(人们平常所使用的程序设计语言大多属于此类型一笔勾销它们为面向过程的语言),这一程设范型的中心点是设计过程,所以程序设计时首先要决定的是问题解所需要的过程,然后设计过程的算法。这类范型的语言必须提供设施给过程(函数)传送变元和返回的值,如何区分不同种类的过程(函数)、如何传送变元是这类程序设计中关心的主要问题。
面向对象程设范型是在以上范型之上发展起来的,它的关键在于加入了类及其继承性,用类表示通用特性,子类继承父类的特性,并可加入新的特性。对象以类为样板被创建。所以在面向对象程设范中,首要的任务是决定所需要的类,每个类应设置足够的操作,并利用继承机制里二地共享共同的特性。
简而言之,面向对象程设范型具有其它范型所缺乏或不具备的特点,极富生命力,能够适应复杂的大型的软件开发。可以肯定地说,这种新的程设范型必将有力地推动软件开发的新的进展。限于篇幅,其它程设范型在此不作细述。
面向对象方法学:OO方法遵循一般的认知方法学的基本概念(即有关演绎--从一般到特殊和归纳--从特殊到一般的完整理论和方法体系)而建立面向对象方法等基础。面向对象方法学要点之一:认为客观世界是由各种"对象"所组成的,任何事物都是对象,每一个对象都有自已的运动规律和内部状态,每一个对象都属于某个对象"类",都是该对象类的一个元素。复杂的对象可以是由相对比较简单的各种对象以某种方式而构成的。不同对象的组合及相互作用就构成了我们要研究、分析和构造的客观系统。面向对象方法学要点之二:是通过类比,发现对象间的相似性,即对象间的共同属性,这就是构成对象类的依据。在?quot;类"、"父类"、"子类"的概念构成对象类的层次关系时,若不加特殊说明,则处在下一层次上的对象可自然地继承位于上一层次上的对象的属性。面向对象方法学龄前要点之三:认为对已分成类的各个对象,可以通过定义一组"方法"来说明该对象的功能,即允许作用于该对象上的各种操作。对象间的相互联系是通过传递"消息"来完成的,消息就是通知对象去完成一个允许作用于该对象的操作,至于该对象将如何完成这个操作的细节,则是封装在相应的对象类的定义中的,细节对于外界是隐蔽的。
可见,OO方法具有很强的类的概念,因此它就能很自然地直观地模拟人类认识客观世界的方式,亦即模拟人类在认知进程中的由一般到特殊的演绎功能或由特殊到一般的归纳功能,类的概念既反映出对象对象的本质属性,又提供了实现对象共享机制的理论根据。
当我们遵照面向对象方法学的思想进行软件系统开发时,首先要行面向对象的分析(OOA――Object Oriented Analysis),其任务是了解问题域所涉及的对象、对象间的关系和作用(即操作),然后构造问题的对象模型,力争该模型能真实地反映出所要解决的"实质问题"。在这一过程中,抽象是最本质、最重要的方法。针对不同的问题性质选择不同的抽象层次,过简或过繁都会影响到对问题的本质属性的了解和解决。
其次就是进行面向对象的设计(OOD――Object Oriented Analysis),即设计软件的对象模型。根据所应用的面向对象软件开发环境的功能强弱不等,在对问题的对象模型的分析基础上,可能要对它进行一定的改造,但应以最少改变原问题域的对象模型为原则。然后就在软件系统内设设计各个对象、对象间的关系(如层次关系、继承关系等)、对象间的通信方式(如消息模式)等,总之是设计各个对?quot;应做些什么"。
最后阶段是面向对象的实现(OOI-- Object Oriented Zmplementation),即指软件功能的编码实现,它包括:每个对象的内部功能的实现;确立对象哪一些处理能力应在哪些类中进行描述;确定并实现系统的界面、输出的形式及其它控制机理等,总之是实现在OOD阶段所规定的各个对象所应完成的任务。
用OO方法进行面向对象程序设计,其基本步骤如下:
(1) 分析确定在问题空间和解空间出现的全部对象及其属性;
(2) 确定应施加于每个对象的操作,即对象固有的处理能力;
(3) 分析对象间的联系,确定对象彼此间传递的消息;
(4) 设计对象的消息模式,消息模式和处理能力共同构成对象的外部特性;
(5) 分析各个对象的外部特性,将具有相同外部特性的对象归为一类,从而确定所需要的类;
(6) 确定类间的继承关系,将各对象的公共性质放在较上层的类中描述,通过继承来共享对公共性质的描述;
(7) 设计每个类关于对象外部特性的描述;
(8) 设计每个类的内部实现(数据结构和方法);
(9) 创建所需的对象(类的实例),实现对象间应有的联系(发消息)。
面向对象技术:技术"泛指根据生产实践经验和自然科学原理
而发展起来的各种工艺操作方法与技能";"广义地讲,还包括相应的生产工具和其它物质设备,以及生产的工艺过程或作业程序、方法"。OO方法既是程序设计新范型、系统开发的新方法学,作为一门新技术它就有了基本的依据,事实上,OO方法可支持种类不同的系统开发地,已经或正在许多方面得以应用,因此,可以说OO方法是一门新的技术――面向对象技术。
近十多年来,除了面向对象的程序设计以外,OO方法已发展应用到整个信息系统领域和一些新兴的工业领域,包括:用户界面(特别是图形用户界面――GUI)、应用集成平台、面向对象数据库(OODB)、分布式系统、网络管理结构、人工智能领域以及并发工程、综合集成工程等。人工智能是和计算机密切相关的新领域,在很多方面已经采用面向对象技术,如知识的表示,专家系统的建造、用户界面等。人工智能的软件通常规模较大,用面向对象技术有可能更好地设计并维护这类程序。
80年代后期形成的并发工程,其概念要点是在产品开发初期(即方案设计阶段)就把结构、工艺、加工、装配、测试、使用、市场等问题同期并行地启动运行,其实现必须有两个基本条件:一是专家群体,二是共享并管理产品信息(将CAD、CAE、CIN紧密结合在一起)。显然,这需要面向对象技术的支持。目前,一些公司采用并发工程组织产品的开发,已取得显著效益:波音公司用以开发巨型777运输机,比开发767节省了一年半时间;日本把并发工程用于新型号的汽车生产,和美国相比只用一半的时间。产业界认为它们念后的生存要依靠并发工程,而面向对象技术是促进并发工程发展的重要支持。
综合集成工程是开发大型开放式复杂统的新的工程概念,和并发工程相似,专家群体的组织和共享信息,是支持这一新工程概念的两大支柱。由于开放式大系统包含人的智能活动,建立数学模型非常困难,而OO方法能够比较自然地刻划现实世界,容易达到问题空间和程序空间的一致,能够在多种层次上支持复杂系统层次模型的建立,是研究综合集成工程的重要工具。
面向对象技术对于并发工程和综合集成工程的作用,一方面说明了这一新技术应用范围的宽广,同时也说明了它的重要影响,更证明了面向对象技术是一门新兴的值得广泛重视的技术。
综上所述,可归纳出OO方法用于系统开发有如下优越性:
(1) 强调从现实世界中客观存在的事物(对象)出发来认识问
题域和构造系统,这就使系统开发者大大减少了对问题域的理解难度,从而使系统能更准确地反映问题域。
(2) 运用人类日常的思维方法和原则(体现于OO方法的抽
象、分类、继承、封装、消息通讯等基本原则)进行系统开发,有益于发挥人类的思维能力,并有效地控制了系 统复杂性。
(3) 对象的概念贯穿于开发过程的终,使各个开发阶段的系统
成分具良好的对应,从而显著地提高了系统的开发效率与质量,并大大降低系统维护的难度。
(4) 对象概念的一致性,使参与系统开发的各类人员在开发的各所段具有共同语言,有效地改善了人员之间的 交流和协作。
(5) 对象的相对稳定性和对易变因素隔离,增强了系统的应变能力。
(6) 对象类之间的继承关系和对象的相对独立性,对软件复用提供了强有力的支持。
OOA方法
面向对象的分析方法(OOA),是在一个系统的开发过程中进行了系统业务调查以后,按照面向对象的思想来分析问题。OOA与结构化分析有较大的区别。OOA所强调的是在系统调查资料的基础上,针对OO方法所需要的素材进行的归类分析和整理,而不是对管理业务现状和方法的分析。
(一)处理复杂问题的原则
用OOA方法对所调查结果进行分析处理时,一般依据以下几项原则:
抽象(abstraction)是指为了某一分析目的而集中精力研究对象的某一性质,它可以忽略其它与此目的无关的部分。在使用这一概念时,我们承认客观世界的复杂性,也知道事物包括有多个细节,但此时并不打算去完整地考虑它。抽象是我们科学地研究和处理复杂问题的重要方法。抽象机制被用在数据分析方面,称之为数据抽象。数据抽象是OOA的核心。数据抽象把一组数据对象以及作用其上的操作组成一个程序实体。使得外部只知道它是如何做和如何表示的。在应用数据抽象原理时,系统分析人员必须确定对象的属性以及处理这些属性的方法,并借助于方法获得属性。在OOA中属性和方法被认为是不可分割的整体。抽象机制有时也被用在对过程的分解方面,被称之为过程抽象。恰当的过程抽象可以对复杂过程的分解和确定以及描述对象发挥积极的作用。
封装(encapsulation)即信息隐蔽。它是指在确定系统的某一部分内容时,应考虑到其它部分的信息及联系都在这一部分的内部进行,外部各部分之间的信息联系应尽可能的少。
继承(inheritance)是指能直接获得已有的性质和特征而不必重复定义它们。OOA可以一次性地指定对象的公共属性和方法,然后再特化和扩展这些属性及方法为特殊情况,这样可大大地减轻在系统实现过程中的重复劳动。在共有属性的基础之上,继承者也可以定义自己独有的特性。
相关(association)是指把某一时刻或相同环境下发生的事物联系在一起。
消息通信(communication with message)是指在对象之间互相传递信息的通信方式。
组织方法。在分析和认识世界时,可综合采用如下三种组织方法(method Of organization):
1。特定对象与其属性之间的区别。
2。整体对象与相应组成部分对象之间的区别。
3。不同对象类的构成及其区别等。
比例(scale)是一种运用整体与部分原则,辅助处理复杂问题的方法。
行为范畴(categories Of behavior)是针对被分析对象而言的,它们主要包括:1。基于直接原因的行为。2。时变性行为。3。功能查询性行为。
(二)OOA方法的基本步骤
在用OOA具体地分析一个事物时,大致上遵循如下五个基本步骤:
第一步,确定对象和类。这里所说的对象是对数据及其处理方式的抽象,它反映了系统保存和处理现实世界中某些事物的信息的能力。类是多个对象的共同属性和方法集合的描述,它包括如何在一个类中建立一个新对象的描述。
第二步,确定结构(structure)。结构是指问题域的复杂性和连接关系。类成员结构反映了泛化-特化关系,整体-部分结构反映整体和局部之间的关系。
第三步,确定主题(subject)。主题是指事物的总体概貌和总体分析模型。
第四步,确定属性(attribute)。属性就是数据元素,可用来描述对象或分类结构的实例,可在图中给出,并在对象的存储中指定。
第五步,确定方法(method)。方法是在收到消息后必须进行的一些处理方法:方法要在图中定义,并在对象的存储中指定。对于每个对象和结构来说,那些用来增加、修改、删除和选择一个方法本身都是隐含的(虽然它们是要在对象的存储中定义的,但并不在图上给出),而有些则是显示的。
OOD方法
面向对象的设计方法是OO方法中一个中间过渡环节。其主要作用是对OOA分析的结果作进一步的规范化整理,以便能够被OOP直接接受。在OOD的设计过程中,要展开的主要有如下几项工作。
(一)对象定义规格的求精过程
对于OOA所抽象出来的对象-&-类以及汇集的分析文档,OOD需要有一个根据设计要求整理和求精的过程,使之更能符合OOP的需要。这个整理和求精过程主要有两个方面:一是要根据面向对象的概念模型整理分析所确定的对象结构、属性、方法等内容,改正错误的内容,删去不必要和重复的内容等。二是进行分类整理,以便于下一步数据库设计和程序处理模块设计的需要。整理的方法主要是进行归类,对类一&一对象、属性、方法和结构、主题进行归类。
(二)数据模型和数据库设计
数据模型的设计需要确定类-&-对象属性的内容、消息连接的方式、系统访问、数据模型的方法等。最后每个对象实例的数据都必须落实到面向对象的库结构模型中。
(三)优化
OOD的优化设计过程是从另一个角度对分析结果和处理业务过程的整理归纳,优化包括对象和结构的优化、抽象、集成。
对象和结构的模块化表示OOD提供了一种范式,这种范式支持对类和结构的模块化。这种模块符合一般模块化所要求的所有特点,如信息隐蔽性好,内部聚合度强和模块之间耦合度弱等。
集成化使得单个构件有机地结合在一起,相互支持。
OO方法当前的研究领域
当前,在研究OO方法的热潮中,有如下主要研究领域:
(1) 智能计算机的研究。因为OO方法可将知识片看作对象,并为相关知识的模块化提供方便,所以在知识工程领域越来越受到重视。OO方法的设计思想被引入到智能计算机的研究中。
(2) 新一代操作系统的研究。采用OO方法来组织设计新一代操作系统具有如下优点:采用对象来描述OS所需要设计、管理的各类资源信息,如文件、打印机、处理机、各类解设等更为自然;引入OO方法来处理OO的诸多事务,如命名、同步、保护、管理等,会更易实现、更便于维护;OO方法对于多机、并发控制可提供有力的支持,并能得当地管理网络,使其更丰富和协调。
(3) 多学科的综合研究。当前,人工智能、数据库、编程语言的研究有汇合趋势。例如,在研究新一代数据库系统(智能数据库系统)中,能否用人工智能思想与OO方法建立描述功能更强的数椐模型?能否将数据库语言和编程语言融为一体?为了实现多学科的综合,OO方法是一个很有希望的汇聚点。
(4) 新一代面向对象的硬件系统的研究。要支持采用OO方法设计的软件系统的运行,必须建立更理想的能支持OO方法的硬件环境。目前采用松耦合(分布主存)结构的多处理机系统更接近于OO方法的思想;作为最新出现的神经网络计算机的体系结构与OO方法的体系结构具有惊人的类似,并能相互支持与配合:一个神经元就是一个小粒度的对象;神经元的连接机制与OO方法的消息传送有着天然的联系;一次连接可以看作一次消息的发送。可以预料,将OO方法与神经网络研究相互结合,必然可以开发出功能更强、更迷人的新一代计算机硬件系统。
五、展望