java面向?qū)ο驩OA、OOD、OOP

OOA:Object-Oriented Analysis面向?qū)ο蠓治龇椒?/b>

是在一個(gè)系統(tǒng)的開發(fā)過程中進(jìn)行了系統(tǒng)業(yè)務(wù)調(diào)查以后,按照面向?qū)ο蟮乃枷雭矸治鰡栴}。OOA與結(jié)構(gòu)化分析有較大的區(qū)別。OOA所強(qiáng)調(diào)的是

在系統(tǒng)調(diào)查資料的基礎(chǔ)上,針對(duì)OO方法所需要的素材進(jìn)行的歸類分析和整理,而不是對(duì)管理業(yè)務(wù)現(xiàn)狀和方法的分析。

OOA(面向?qū)ο蟮姆治觯┠P陀?個(gè)層次(主題層、對(duì)象類層、結(jié)構(gòu)層、屬性層和服務(wù)層)和5個(gè)活動(dòng)(標(biāo)識(shí)對(duì)象類、標(biāo)識(shí)結(jié)構(gòu)、定義主題

、定義屬性和定義服務(wù))組成。在這種方法中定義了兩種對(duì)象類之間的結(jié)構(gòu),一種稱為分類結(jié)構(gòu),一種稱為組裝結(jié)構(gòu)。分類結(jié)構(gòu)就是所謂的一

般與特殊的關(guān)系。組裝結(jié)構(gòu)則反映了對(duì)象之間的整體與部分的關(guān)系。

OOA在定義屬性的同時(shí),要識(shí)別實(shí)例連接。實(shí)例連接是一個(gè)實(shí)例與另一個(gè)實(shí)例的映射關(guān)系。

OOA在定義服務(wù)的同時(shí)要識(shí)別消息連接。當(dāng)一個(gè)對(duì)象需要向另一對(duì)象發(fā)送消息時(shí),它們之間就存在消息連接。

OOA 中的5個(gè)層次和5個(gè)活動(dòng)繼續(xù)貫穿在OOD(畫向?qū)ο蟮脑O(shè)計(jì))過程中。OOD模型由4個(gè)部分組成。它們分別是設(shè)計(jì)問題域部分、設(shè)計(jì)人機(jī)

交互部分、設(shè)計(jì)任務(wù)管理部分和設(shè)計(jì)數(shù)據(jù)管理部分。

一、OOA的主要原則:

(1)抽象:從許多事物中舍棄個(gè)別的、非本質(zhì)的特征,抽取共同的、本質(zhì)性的特征,就叫作抽象。抽象是形成概念的必須手段。

抽象原則有兩方面的意義:第一,盡管問題域中的事物是很復(fù)雜的,但是分析員并不需要了解和描述它們的一切,只需要分析研究其中與

系統(tǒng)目標(biāo)有關(guān)的事物及其本質(zhì)性特征。第二,通過舍棄個(gè)體事物在細(xì)節(jié)上的差異,抽取其共同特征而得到一批事物的抽象概念。

抽象是面向?qū)ο蠓椒ㄖ惺褂米顬閺V泛的原則。抽象原則包括過程抽象和數(shù)據(jù)抽象兩個(gè)方面。

過程抽象是指,任何一個(gè)完成確定功能的操作序列,其使用者都可以把它看作一個(gè)單一的實(shí)體,盡管實(shí)際上它可能是由一系列更低級(jí)的操

作完成的。

數(shù)據(jù)抽象是根據(jù)施加于數(shù)據(jù)之上的操作來定義數(shù)據(jù)類型,并限定數(shù)據(jù)的值只能由這些操作來修改和觀察。數(shù)據(jù)抽象是OOA的核心原則。它

強(qiáng)調(diào)把數(shù)據(jù)(屬性)和操作(服務(wù))結(jié)合為一個(gè)不可分的系統(tǒng)單位(即對(duì)象),對(duì)象的外部只需要知道它做什么,而不必知道它如何做。

(2)封裝就是把對(duì)象的屬性和服務(wù)結(jié)合為一個(gè)不可分的系統(tǒng)單位,并盡可能隱蔽對(duì)象的內(nèi)部細(xì)節(jié)。

(3)繼承:特殊類的對(duì)象擁有的其一般類的全部屬性與服務(wù),稱作特殊類對(duì)一般類的繼承。

在OOA中運(yùn)用繼承原則,就是在每個(gè)由一般類和特殊類形成的一般—特殊結(jié)構(gòu)中,把一般類的對(duì)象實(shí)例和所有

特殊類的對(duì)象實(shí)例都共同具

有的屬性和服務(wù),一次性地在一般類中進(jìn)行顯式的定義。在特殊類中不再重復(fù)地定義一般類中已定義的東西,但是在語義上,特殊類卻自動(dòng)地

、隱含地?fù)碛兴囊话泐悾ㄒ约八懈蠈拥囊话泐悾┲卸x的全部屬性和服務(wù)。繼承原則的好處是:使系統(tǒng)模型比較簡練也比較清晰。

(4)分類:就是把具有相同屬性和服務(wù)的對(duì)象劃分為一類,用類作為這些對(duì)象的抽象描述。分類原則實(shí)際上是抽象原則運(yùn)用于對(duì)象描述

時(shí)的一種表現(xiàn)形式。

(5)聚合:又稱組裝,其原則是:把一個(gè)復(fù)雜的事物看成若干比較簡單的事物的組裝體,從而簡化對(duì)復(fù)雜事物的描述。

(6)關(guān)聯(lián):是人類思考問題時(shí)經(jīng)常運(yùn)用的思想方法:通過一個(gè)事物聯(lián)想到另外的事物。能使人發(fā)生聯(lián)想的原因是事物之間確實(shí)存在著某

些聯(lián)系。

(7)消息通信:這一原則要求對(duì)象之間只能通過消息進(jìn)行通信,而不允許在對(duì)象之外直接地存取對(duì)象內(nèi)部的屬性。通過消息進(jìn)行通信是

由于封裝原則而引起的。在OOA中要求用消息連接表示出對(duì)象之間的動(dòng)態(tài)聯(lián)系。

(8)粒度控制:一般來講,人在面對(duì)一個(gè)復(fù)雜的問題域時(shí),不可能在同一時(shí)刻既能縱觀全局,又能洞察秋毫。因此需要控制自己的視野

:考慮全局時(shí),注意其大的組成部分,暫時(shí)不詳察每一部分的具體的細(xì)節(jié);考慮某部分的細(xì)節(jié)時(shí)則暫時(shí)撇開其余的部分。這就是粒度控制原則

。

(9)行為分析:現(xiàn)實(shí)世界中事物的行為是復(fù)雜的。由大量的事物所構(gòu)成的問題域中各種行為往往相互依賴、相互交織。

二、面向?qū)ο蠓治霎a(chǎn)生三種分析模型:

1、對(duì)象模型:對(duì)用例模型進(jìn)行分析,把系統(tǒng)分解成互相協(xié)作的分析類,通過類圖/對(duì)象圖描述對(duì)象/對(duì)象的屬性/對(duì)象間的關(guān)系,是系統(tǒng)的靜態(tài)

模型

2、動(dòng)態(tài)模型:描述系統(tǒng)的動(dòng)態(tài)行為,通過時(shí)序圖/協(xié)作圖描述對(duì)象的交互,以揭示對(duì)象間如何協(xié)作來完成每個(gè)具體的用例,單個(gè)對(duì)象的狀態(tài)變

化/動(dòng)態(tài)行為可以通過狀態(tài)圖來表達(dá)

3、功能模型(即用例模型à作為輸入)。

三、OOA的主要優(yōu)點(diǎn):

(1)加強(qiáng)了對(duì)問題域和系統(tǒng)責(zé)任的理解;

(2)改進(jìn)與分析有關(guān)的各類人員之間的交流;

(3)對(duì)需求的變化具有較強(qiáng)的適應(yīng)性;

(4)支持軟件復(fù)用。

(5)貫穿軟件生命周期全過程的一致性。

(6)實(shí)用性;

(7)有利于用戶參與。

四、OOA方法的基本步驟:

在用OOA具體地分析一個(gè)事物時(shí),大致上遵循如下五個(gè)基本步驟:

第一步,確定對(duì)象和類。這里所說的對(duì)象是對(duì)數(shù)據(jù)及其處理方式的抽象,它反映了系統(tǒng)保存和處理現(xiàn)實(shí)世界中某些事物的信息的能力。類

是多個(gè)對(duì)象的共同屬性和方

法集合的描述,它包括如何在一個(gè)類中建立一個(gè)新對(duì)象的描述。

第二步,確定結(jié)構(gòu)(structure)。結(jié)構(gòu)是指問題域的復(fù)雜性和連接關(guān)系。類成員結(jié)構(gòu)反映了泛化-特化關(guān)系,整體-部分結(jié)構(gòu)反映整體和

局部之間的關(guān)系。

第三步,確定主題(subject)。主題是指事物的總體概貌和總體分析模型。

第四步,確定屬性(attribute)。屬性就是數(shù)據(jù)元素,可用來描述對(duì)象或分類結(jié)構(gòu)的實(shí)例,可在圖中給出,并在對(duì)象的存儲(chǔ)中指定。

第五步,確定方法(method)。方法是在收到消息后必須進(jìn)行的一些處理方法:方法要在圖中定義,并在對(duì)象的存儲(chǔ)中指定。對(duì)于每個(gè)對(duì)

象和結(jié)構(gòu)來說,那些用來增加、修改、刪除和選擇一個(gè)方法本身都是隱含的(雖然它們是要在對(duì)象的存儲(chǔ)中定義的,但并不在圖上給出),而

有些則是顯示的。

OOP

目錄[隱藏]

一、OOP的基本思想

二、OOP技術(shù)的歷史

三、OOP 的優(yōu)缺點(diǎn)

四、OOP的未來

五、不同OOP語言各有什么優(yōu)勢(shì)和劣勢(shì)?

六、發(fā)展 vs. 革新

OOP: Object Oriented Programming,面向?qū)ο蟮某绦蛟O(shè)計(jì)

所謂“對(duì)象”就是一個(gè)或一組數(shù)據(jù)以及處理這些數(shù)據(jù)的方法和過程的集合。面向?qū)ο蟮某绦蛟O(shè)計(jì)完全不同于傳統(tǒng)的 面向過程程序設(shè)計(jì),它大大地降低了軟件開發(fā)的難度,使編程就像搭積木一樣簡單,是當(dāng)今電腦編程的一股勢(shì)不可擋的潮流。

面向?qū)ο缶幊蹋∣bject Oriented Programming,OOP,面向?qū)ο蟪绦蛟O(shè)計(jì))是一種計(jì)算機(jī)編程架構(gòu)。OOP 的一條基本原則是計(jì)算機(jī)程序是由單個(gè)能夠起到子程序作用的單元或?qū)ο蠼M合而成。OOP 達(dá)到了軟件工程的三個(gè)主要目標(biāo):重用性、靈活性和擴(kuò)展性。為了實(shí)現(xiàn)整體運(yùn)算,每個(gè)對(duì)象都能夠接收信息、處理數(shù)據(jù)和向其它對(duì)象發(fā)送信息。OOP 主要有以下的概念和組件:

組件 - 數(shù)據(jù)和功能一起在運(yùn)行著的計(jì)算機(jī)程序中形成的單元,組件在 OOP 計(jì)算機(jī)程序中是模塊和結(jié)構(gòu)化的基礎(chǔ)。

抽象性 - 程序有能力忽略正在處理中信息的某些方面,即對(duì)信息主要方面關(guān)注的能力。

封裝 - 也叫做信息封裝:確保組件不會(huì)以不可預(yù)期的方式改變其它組件的內(nèi)部狀態(tài);只有在那些提供了內(nèi)部狀態(tài)改變方法的組件中,才可以訪問其內(nèi)部狀態(tài)。每類組件都提 供了一個(gè)與其它組件聯(lián)系的接口,并規(guī)定了其它組件進(jìn)行調(diào)用的方法。

多態(tài)性 - 組件的引用和類集會(huì)涉及到其它許多不同類型的組件,而且引用組件所產(chǎn)生的結(jié)果得依據(jù)實(shí)際調(diào)用的類型。

繼承性 - 允許在現(xiàn)存的組件基礎(chǔ)上創(chuàng)建子類組件,這統(tǒng)一并增強(qiáng)了多態(tài)性和封裝性。典型地來說就是用類來對(duì)組件進(jìn)行分組,而且還可以定義新類為現(xiàn)存的類的擴(kuò)展,這樣就 可以將

類組織成樹形或網(wǎng)狀結(jié)構(gòu),這體現(xiàn)了動(dòng)作的通用性。

由于抽象性、封裝性、重用性以及便于使用等方面的原因,以組件為基礎(chǔ)的編程在腳本語言中已經(jīng)變得特別流行。Python 和 Ruby 是最近才出現(xiàn)的語言,在開發(fā)時(shí)完全采用了 OOP 的思想,而流行的 Perl 腳本語言從版本5開始也慢慢地加入了新的面向?qū)ο蟮墓δ芙M件。用組件代替“現(xiàn)實(shí)”上的實(shí)體成為 JavaScript(ECMAScript)得以流行的原因,有論證表明對(duì)組件進(jìn)行適當(dāng)?shù)慕M合就可以在英特網(wǎng)上代替 HTML 和 XML 的文檔對(duì)象模型(DOM)。

[編輯本段]

一、OOP的基本思想

OOP的許多原始思想都來之于Simula語言,并在Smalltalk語言的完善和標(biāo)準(zhǔn)化過程中得到更多的擴(kuò)展和對(duì)以前的思想的重新注解??梢哉f OO 思想和OOPL幾乎是同步發(fā)展相互促進(jìn)的。與函數(shù)式程序設(shè)計(jì)(functional-programming)和邏輯式程序設(shè)計(jì)(logic- programming)所代表的接近于機(jī)器的實(shí)際計(jì)算模型所不同的是,OOP幾乎沒有引入精確的數(shù)學(xué)描敘,而是傾向于建立一個(gè)對(duì)象模型,它能夠近似的反 映應(yīng)用領(lǐng)域內(nèi)的實(shí)體之間的關(guān)系,其本質(zhì)是更接近于一種人類認(rèn)知事物所采用的哲學(xué)觀的計(jì)算模型。由此,導(dǎo)致了一個(gè)自然的話題,那就是OOP到底是什么? [D&T 1988][B.S 1991] .。在OOP中,對(duì)象作為計(jì)算主體,擁有自己的名稱,狀態(tài)以及接受外界消息的接口。在對(duì)象模型中,產(chǎn)生新對(duì)象,舊對(duì)象銷毀,發(fā)送消息,響應(yīng)消息就構(gòu)成 OOP計(jì)算模型的根本。

對(duì)象的產(chǎn)生有兩種基本方式。一種是以原型(prototype)對(duì)象為基礎(chǔ)產(chǎn)生新的對(duì)象。一種是以類(class)為基礎(chǔ)產(chǎn)生新對(duì)象。原型的概念已經(jīng) 在認(rèn)知心理學(xué)中被用來解釋概念學(xué)習(xí)的遞增特性,原型模型本身就是企圖通過提供一個(gè)有代表性的對(duì)象為基礎(chǔ)來產(chǎn)生各種新的對(duì)象,并由此繼續(xù)產(chǎn)生更符合實(shí)際應(yīng)用 的對(duì)象。而原型-委托也是OOP中的對(duì)象抽象,代碼共享機(jī)制中的一種。一個(gè)類提供了一個(gè)或者多個(gè)對(duì)象的通用性描敘。從形式化的觀點(diǎn)看,類與類型有關(guān),因此 一個(gè)類相當(dāng)于是從該類中產(chǎn)生的實(shí)例的集合。而這樣的觀點(diǎn)也會(huì)帶來一些矛盾,比較典型的就是在繼承體系下,子集(子類)對(duì)象和父集(父類)對(duì)象之間的行為相 融性可能很難達(dá)到,這也就是OOP中常被引用的---子類型(subtype)不等于子類(subclass)[Budd 2002]。而在一種所有皆對(duì)象的世界觀背景下,在類模型基礎(chǔ)上還誕生出了一種擁有元類(metaclass)的新對(duì)象模型。即類本身也是一種其他類的對(duì) 象。以上三種根本不同的觀點(diǎn)各自定義了三種基于類(class-based),基于原型(prototype-based)和基于元類 (metaclass-based)的對(duì)象模型。而這三種對(duì)象模型也就導(dǎo)致了許多不同的

程序設(shè)計(jì)語言(如果我們暫時(shí)把靜態(tài)與動(dòng)態(tài)的差別放在一邊)。是的, 我們經(jīng)常接觸的C++,Java都是使用基于類的對(duì)象模型,但除此之外還有很多我們所沒有接觸的OOPL采用了完全不一樣的對(duì)象模型,他們是在用另外一種 觀點(diǎn)詮釋OOP的內(nèi)涵。

什么是oop的基本思想呢?把組件的實(shí)現(xiàn)和接口分開,并且讓組件具有多態(tài)性。不過,兩者還是有根本的不同。oop強(qiáng)調(diào)在程序構(gòu)造中語言要素的語法。你 必須得繼承,使用類,使用對(duì)象,對(duì)象傳遞消息。gp不關(guān)心你繼承或是不繼承,它的開端是分析產(chǎn)品的分類,有些什么種類,他們的行為如何。就是說,兩件東西 相等意味著什么?怎樣正確地定義相等操作?不單單是相等操作那么簡單,你往深處分析就會(huì)發(fā)現(xiàn)“相等”這個(gè)一般觀念意味著兩個(gè)對(duì)象部分,或者至少基本部分是 相等的,據(jù)此我們就可以有一個(gè)通用的相等操作。再說對(duì)象的種類。假設(shè)存在一個(gè)順序序列和一組對(duì)于順序序列的操作。那么這些操作的語義是什么?從復(fù)雜度權(quán)衡 的角度看,我們應(yīng)該向用戶提供什么樣的順序序列?該種序列上存在那些操作?那種排序是我們需要的?只有對(duì)這些組件的概念型分類搞清楚了,我們才能提到實(shí)現(xiàn) 的問題:使用模板、繼承還是宏?使用什么語言和技術(shù)?gp的基本觀點(diǎn)是把抽象的軟件組件和它們的行為用標(biāo)準(zhǔn)的分類學(xué)分類,出發(fā)點(diǎn)就是要建造真實(shí)的、高效的 和不取決于語言的算法和數(shù)據(jù)結(jié)構(gòu)。當(dāng)然最終的載體還是語言,沒有語言沒法編程。stl使用 c++,你也可以用ada來實(shí)現(xiàn),用其他的語言來實(shí)現(xiàn)也行,結(jié)果會(huì)有所不同,但基本的東西是一樣的。到處都要用到二分查找和排序,而這就是人們正在做的。 對(duì)于容器的語義,不同的語言會(huì)帶來輕微的不同。但是基本的區(qū)別很清楚是gp所依存的語義,以及語義分解。例如,我們決定需要一個(gè)組件swap,然后指出這 個(gè)組件在不同的語言中如果工作。顯然重點(diǎn)是語義以及語義分類。而oop所強(qiáng)調(diào)的(我認(rèn)為是過分強(qiáng)調(diào)的)是清楚的定義類之間的層次關(guān)系。oop告訴了你如何 建立層次關(guān)系,卻沒有告訴你這些關(guān)系的實(shí)質(zhì)。

(這段不太好理解,有一些術(shù)語可能要過一段時(shí)間才會(huì)有合適的中文翻譯——譯者)

面向?qū)ο蟮木幊谭椒∣OP是九十年代才流行的一種軟件編程方法。它強(qiáng)調(diào)對(duì)象的“抽象”、“封裝”、“繼承”、“多態(tài)”。我們講程序設(shè)計(jì)是由“數(shù)據(jù)結(jié) 構(gòu)”+“算法”組成的。從宏觀的角度講,OOP下的對(duì)象是以編程為中心的,是面向程序的對(duì)象。我們今天要講的OOD是面向信息的對(duì)象,是以用戶信息為中心 的。

[編輯本段]

二、OOP技術(shù)的歷史

面向?qū)ο蠹夹g(shù)最初是從面向?qū)?/p>

象的程序設(shè)計(jì)開始的,它的出現(xiàn)以60年代simula語言為標(biāo)志。80年代中后期,面向?qū)ο蟪绦蛟O(shè)計(jì)逐漸成熟,被計(jì)算機(jī)界 理解和接受,人們又開始進(jìn)一步考慮面向?qū)ο蟮拈_發(fā)問題。這就是九十年代以Microsoft Visual系列OOP軟件的流行的背景。

傳統(tǒng)的結(jié)構(gòu)化分析與設(shè)計(jì)開發(fā)方法是一個(gè)線性過程,因此,傳統(tǒng)的結(jié)構(gòu)化分析與設(shè)計(jì)方法要求現(xiàn)實(shí)系統(tǒng)的業(yè)務(wù)管理規(guī)范,處理數(shù)據(jù)齊全,用戶能全面完整地其業(yè) 務(wù)需求。

傳統(tǒng)的軟件結(jié)構(gòu)和設(shè)計(jì)方法難以適應(yīng)軟件生產(chǎn)自動(dòng)化的要求,因?yàn)樗赃^程為中心進(jìn)行功能組合,軟件的擴(kuò)充和復(fù)用能力很差。

對(duì)象是對(duì)現(xiàn)實(shí)世界實(shí)體的模擬,因面能更容易地理解需求,即使用戶和分析者之間具有不同的教育背景和工作特點(diǎn),也可很好地溝通。

區(qū)別面向?qū)ο蟮拈_發(fā)和傳統(tǒng)過程的開發(fā)的要素有:對(duì)象識(shí)別和抽象、封裝、多態(tài)性和繼承。

對(duì)象(Object)是一個(gè)現(xiàn)實(shí)實(shí)體的抽象,由現(xiàn)實(shí)實(shí)體的過程或信息牲來定義。一個(gè)對(duì)象可被認(rèn)為是一個(gè)把數(shù)據(jù)(屬性)和程序(方法)封裝在一起的實(shí) 體,這個(gè)程序產(chǎn)生該對(duì)象的動(dòng)作或?qū)λ邮艿降耐饨缧盘?hào)的反應(yīng)。這些對(duì)象操作有時(shí)稱為方法。對(duì)象是個(gè)動(dòng)態(tài)的概念,其中的屬性反映了對(duì)象當(dāng)前的狀態(tài)。

類(Class)用來描述具有相同的屬性和方法的對(duì)象的集合。它定義了該集合中每個(gè)對(duì)象所共有的屬性和方法。對(duì)象是類的實(shí)例。

由上分析不難看出,盡管OOP技術(shù)更看中用戶的對(duì)象模型,但其目的都是以編程為目的的,而不是以用戶的信息為中心的,總想把用戶的信息納入到某個(gè)用戶 不感興趣的“程序?qū)ο蟆敝小?/p>

[編輯本段]

三、OOP 的優(yōu)缺點(diǎn)

· OOP 的優(yōu)點(diǎn):使人們的編程與實(shí)際的世界更加接近,所有的對(duì)象被賦予屬性和方法,結(jié)果編程就更加富有人性化。

· OOP 的也有缺點(diǎn),就 C++ 而言,由于面向更高的邏輯抽象層,使得 C++ 在實(shí)現(xiàn)的時(shí)候,不得不做出性能上面的犧牲,有時(shí)候甚至是致命的 ( 所有對(duì)象的屬性都經(jīng)過內(nèi)置多重指針的間接引用是其性能損失的主要原因之一;不過,筆者的局限性在于未使用過 VC++ 外的面向?qū)ο笳Z言,所以不是十分肯定,哈哈,有人笑出來了… )。

在計(jì)算機(jī)速度飛速發(fā)展的今天,你可能會(huì)說,一丁點(diǎn)的性能犧牲沒什么大不了。是的,從面向?qū)ο蟮慕嵌龋沟木幊痰慕Y(jié)構(gòu)更加清晰完整,數(shù)據(jù)更加獨(dú)立和易于 管理,性能的犧牲可以帶來這么多的好處,沒有理由不做穩(wěn)賺的生意吧?

不過,在某些對(duì)速度要求極高特殊場合,例如你做的是電信的交換系統(tǒng),每秒鐘有超過百萬的人同時(shí)進(jìn)行電話交換,如果,每一個(gè)數(shù)據(jù)交換過程都是一個(gè)對(duì)象, 那么總的性能損失將是天文數(shù)字!!

或者這個(gè)例子不夠貼身,再舉個(gè)例子吧。假如你受聘于一個(gè)游戲設(shè)計(jì)公司,老板希望做出來的游戲可以更多的兼顧到更多的電腦使用者,游戲每秒鐘的運(yùn)行的幀 可以更多,子彈和爆炸物可以更多、更華麗。那么,你會(huì)發(fā)現(xiàn)使用 C++ 會(huì)使你的程序變得笨拙,無法滿足你的需求,除非你非得要你的游戲運(yùn)行于奔騰四的機(jī)器上 ( 如果不是,而你又堅(jiān)持用 C++ 的對(duì)象編程,那么請(qǐng)減少主角的槍的威力吧 )。

如果你是冥頑不寧的人,你說不相信 OOP 會(huì)有性能上的損失,那么,我記得曾看到在 CSDN 上關(guān)于 VB 和 VC 執(zhí)行效率的討論的文章,講述的就是使用了 MFC 以后,執(zhí)行效率甚至低于 VB 開發(fā)出來的東西。請(qǐng)各位驗(yàn)證一下:如果使用的是純粹的 C 語言語法的話,那么一定會(huì)比在 VB 編出來的東西要快很多 ( GetTickCount 函數(shù)可以查閱 MSDN ,如果想更加精確一些,可以使用 QueryPerformanceCounter 函數(shù) )。

[編輯本段]

四、OOP的未來

(撰文/Bjarne Stroustrup & Tim Lindholm 編譯/孟巖)

在未來三年,程序員編寫代碼的方式會(huì)發(fā)生那些變化?

Stroustrup: 在C++中,假如沒有合適的庫在背后支撐,完成任何重要的工作都可能是很復(fù)雜的。而一旦有了合適的庫,任何東西都可以被我們操控于股掌之間。因此,構(gòu)造和 使用程序庫的重要性與日俱增。這也暗示我們,泛型程序設(shè)計(jì)(generic programming)將會(huì)越來越多地被運(yùn)用。只有通過GP,我們才能確保庫的通用性和高效率。我還預(yù)期在分布式計(jì)算和“組件 (components)”應(yīng)用領(lǐng)域會(huì)出現(xiàn)喜人的增長。就大部分程序員而言,通過使用方便適用的程序庫,這些開發(fā)工作會(huì)變得簡單明了。

現(xiàn)在有一個(gè)趨勢(shì),編譯器廠商試圖把其特有的“對(duì)象模型”和圖形界面(GUI)細(xì)節(jié)推銷給用戶。比如微軟的COM和Inprise的類屬性 “properties”。對(duì)于用戶來說,這既不必要,也不情愿。我所希望看到的程序庫,應(yīng)該是用標(biāo)準(zhǔn)C++打造,界面靈活,值得信賴的程序庫。通常,這 些界面應(yīng)該是平臺(tái)無關(guān)的。C++的表達(dá)能力極強(qiáng),即使不使用大量的宏,也應(yīng)該足以達(dá)成這一要求。就算有些地方無法百分之百的遵守這一原則,也應(yīng)該將對(duì)于平 臺(tái)和廠家的依賴性限制起來。這個(gè)目標(biāo)的完成情況,可以反映軟件工具產(chǎn)業(yè)對(duì)于應(yīng)用程序開發(fā)行業(yè)的關(guān)注程度。我懷疑目前對(duì)于那些獨(dú)立的、跨平臺(tái)廠商來說,并不 存在相應(yīng)的市場。如果能夠建立這樣的市場,也許能夠促進(jìn)廠商們?yōu)榭蛻糇龀觥罢嬲杏玫摹碑a(chǎn)品。

Lindholm: 對(duì)于編寫代碼的開發(fā)者來說,主要的驅(qū)動(dòng)力量仍將是兩個(gè):網(wǎng)絡(luò)和分布式——也就是設(shè)計(jì)和開發(fā)非單機(jī)軟件的需求。大部分的應(yīng)用程序?qū)⒉粫?huì)是孤零零地運(yùn)行在單一 設(shè)備上

,而是運(yùn)用了類似EJB和JSP之類技術(shù)的,平臺(tái)無關(guān)的分布式程序。程序員們將不得不面對(duì)分布式計(jì)算的重重險(xiǎn)阻。這將對(duì)許多程序員所依賴的設(shè)計(jì)模 式、技術(shù)和直覺構(gòu)成嚴(yán)峻的挑戰(zhàn)。這是選擇編程語言之前必須認(rèn)識(shí)到的,盡管不同語言的設(shè)計(jì)特性可能促進(jìn)或者阻礙這一轉(zhuǎn)化。

在網(wǎng)絡(luò)應(yīng)用的增長中,一個(gè)很重要的部分是小型移動(dòng)設(shè)備和特殊Internet設(shè)備的爆炸性增長。這些設(shè)備各有各的操作系統(tǒng),或者只在某種特定的設(shè)備領(lǐng) 域內(nèi)有共同的操作系統(tǒng)。我們現(xiàn)在還可以一一列舉出這些設(shè)備——家庭接入設(shè)備、蜂窩電話、電子報(bào)紙、PDA、自動(dòng)網(wǎng)絡(luò)設(shè)備等等。但是這些設(shè)備領(lǐng)域的數(shù)量和深 入程度將會(huì)很快變得難以估量。我們都知道這個(gè)市場大得驚人,PC的興起與之相比不過小菜一碟。因此在這些設(shè)備的應(yīng)用程序市場上,競爭將會(huì)相當(dāng)殘酷。獲勝的 重要手段之一,就是盡快進(jìn)入市場。開發(fā)人員需要優(yōu)秀的工具,迅速高效地撰寫和調(diào)試他們的軟件。平臺(tái)無關(guān)性也是制勝秘訣之一,它使得程序員能夠開發(fā)出支持多 種設(shè)備平臺(tái)的軟件。

我預(yù)期的另一個(gè)變化是,我們對(duì)于代碼(Java)和數(shù)據(jù)(XML)協(xié)同型應(yīng)用程序的開發(fā)能力將會(huì)不斷提高。這種協(xié)同是開發(fā)強(qiáng)大應(yīng)用程序的核心目標(biāo)之 一。我們從XML的迅速流行和ebXML規(guī)范的進(jìn)展中,已經(jīng)看到了這個(gè)趨勢(shì)。ebXML是一個(gè)針對(duì)電子商務(wù)和國際貿(mào)易的,基于XML的開放式基礎(chǔ)構(gòu)架,由 聯(lián)合國貿(mào)易促進(jìn)和電子商務(wù)中心(UN/CEFACT)與結(jié)構(gòu)性信息標(biāo)準(zhǔn)推進(jìn)組織(OASIS)共同開發(fā)。

我們能否期望出現(xiàn)一個(gè)真正的面向組件(component-oriented)的語言?它的創(chuàng)造者會(huì)是誰呢?

Stroustrup: 我懷疑,這個(gè)領(lǐng)域中之所以缺乏成果,正是因?yàn)槿藗儭饕悄切┓浅绦騿T們——對(duì)“組件”這個(gè)意義含糊的字眼寄予了太多的期望。這些人士夢(mèng)想,有朝一日, 組件會(huì)以某種方式把程序員趕出歷史舞臺(tái)。以后那些稱職的“設(shè)計(jì)員”只需利用預(yù)先調(diào)整好的組件,把鼠標(biāo)拖一拖放一放,就把系統(tǒng)組合出來。對(duì)于軟件工具廠商來 說,這種想法還有另一層意義,他們認(rèn)為,到時(shí)候只有他們才保留有必要的技術(shù),有能力編寫這樣的組件。

這種想法有一個(gè)最基本的謬誤:這種組件很難獲得廣泛歡迎。一個(gè)單獨(dú)的組件或框架 (framework),如果能夠滿足一個(gè)應(yīng)用程序或者一個(gè)產(chǎn)業(yè)領(lǐng)域?qū)λ岢龅拇蟛糠忠蟮脑?,?duì)于其制造者來說就是劃算的產(chǎn)品,而且技術(shù)上也不是很困 難??墒窃摦a(chǎn)業(yè)內(nèi)的幾個(gè)競爭者很快就會(huì)發(fā)現(xiàn),如果所有人都采用這些組件,那么彼此之間的產(chǎn)品就會(huì)變得天下大同,沒什么區(qū)別,他們將淪為簡單的辦事員,主要 利潤都將鉆進(jìn)那些組件/框架供應(yīng)商的腰包里!

小“組件”很有用,不過產(chǎn)生不了預(yù)期的杠桿效應(yīng)。中型的、更通用的組件非常有用,但是構(gòu)造時(shí)需要非同尋常的彈性。

在C++中,我們綜合運(yùn)用不同共享形式的類體系(class hierarchies),以及使用templates精心打造的接口,在這方面取得了一定的進(jìn)展。我期待在這個(gè)領(lǐng)域取得一些有趣和有用的成果,不過我認(rèn) 為這種成果很可能是一種新的C++程序設(shè)計(jì)風(fēng)格,而不是一種新的語言。

Lindholm: 編寫面向組件的應(yīng)用程序,好像更多的是個(gè)投資、設(shè)計(jì)和程序員管理方面的問題,而不是一個(gè)編程語言問題。當(dāng)然某些語言在這方面具有先天優(yōu)勢(shì),不過如果說有什 么魔術(shù)般的新語言能夠大大簡化組件的編寫難度,那純粹是一種誤導(dǎo)。

微軟已經(jīng)將全部賭注押在C#上,其他語言何去何從?

Stroustrup: C++在下一個(gè)十年里仍然將是一種主流語言。面對(duì)新的挑戰(zhàn),它會(huì)奮起應(yīng)對(duì)。一個(gè)創(chuàng)造了那么多出色系統(tǒng)的語言,絕不會(huì)“坐視落花流水春去也”。

我希望微軟認(rèn)識(shí)到,它在C++(我指的是ISO標(biāo)準(zhǔn)C++)上有著巨大的利益,C++是它與IT世界內(nèi)其他人之間的一座橋梁,是構(gòu)造大型系統(tǒng)和嵌入式 系統(tǒng)的有效工具,也是滿足高性能需求的利器。其他語言,似乎更注重那些四平八穩(wěn)的商用程序。

競爭

C#會(huì)不會(huì)獲得廣泛的接受,并且擠掉其他的語言?

Lindholm: 通常,一種語言既不會(huì)從別的語言那里獲利,也不會(huì)被擠掉。那些堅(jiān)定的Fortran程序員不還用著Fortran嗎?對(duì)于個(gè)人來說,語言的選擇當(dāng)然因時(shí)而 異,但就整體而言,語言的種類只會(huì)遞增,也就是說,它們之間的關(guān)系是“有你有我”而不是“有你沒我”。

對(duì)于一個(gè)新語言的接受程度,往往取決于其能力所及。Java技術(shù)被迅速接受,原因是多方面的,Internet和World Wide Web接口,在其他技術(shù)面前的挫折感,對(duì)于Java技術(shù)發(fā)展方向的全面影響能力,都是原因。另一個(gè)重要的原因是Java獨(dú)立于廠商,這意味著在兼容產(chǎn)品面 前可以從容選擇。

C#是否會(huì)獲得廣泛接受?視情況而定??偟膩碚f,那些對(duì)于平臺(tái)無關(guān)性和廠商無關(guān)性漠不關(guān)心的程序員,可能會(huì)喜歡C#。那些跟微軟平臺(tái)捆在一起人當(dāng)然可 能想要尋找VB 和VC的一個(gè)出色的替代品。但是對(duì)于程序跨平臺(tái)執(zhí)行能力特別關(guān)注的程序員,將會(huì)堅(jiān)守Java之類的語言。這種能力對(duì)于多重訪問設(shè)備(multiple access devices)和分布式計(jì)算模型至關(guān)重要,而Java語言提供了一個(gè)標(biāo)準(zhǔn)的、獨(dú)立于廠商運(yùn)行時(shí)環(huán)境。

Stroustrup:C#的流行程度幾乎完全取決于微軟投入的資金多少??瓷先#的興起肯定會(huì)犧牲掉其他一些語言的利益,但是事實(shí)上未必如此。 Java的蓬勃發(fā)展并沒有給C++帶來衰敗。C++的應(yīng)用仍然在穩(wěn)定增長(當(dāng)然,

已經(jīng)不是爆炸性的增長了)。也許其他的語言也還能獲得自己的一席之地。

不過,我實(shí)在看不出有什么必要再發(fā)明一種新的專有語言。特別是微軟,既生VB,何需C#?

[編輯本段]

五、不同OOP語言各有什么優(yōu)勢(shì)和劣勢(shì)?

Stroustrup: C++的優(yōu)點(diǎn)自始至終都是這么幾條:靈活、高效,而且并非專有語言。現(xiàn)在ISO C++標(biāo)準(zhǔn)的出現(xiàn),鞏固了最后一點(diǎn)。

我認(rèn)為C++的高效是它最基本的優(yōu)點(diǎn)。這種高效來自于其特有的數(shù)據(jù)和計(jì)算模型,較之Java和 C#,這種模型更加貼近機(jī)器。不過,哪些程序才真正地渴望這么高的效率?這是個(gè)問題。我認(rèn)為這類程序非常多。人們對(duì)于計(jì)算機(jī)的期望,永遠(yuǎn)都超越硬件科技的 發(fā)展速度。很顯然,Java和C#的設(shè)計(jì)者的想法不同,他們認(rèn)為,在很多地方效率問題無關(guān)緊要。

C++主要的缺點(diǎn),歸罪于糟糕的教育(是那些始終認(rèn)為C++是個(gè)純粹面向?qū)ο笳Z言的人,和那些把C++當(dāng)成C語言變體的人導(dǎo)致了這種情況),歸罪于不 同平臺(tái)上的不一致性,歸罪于不完整、不標(biāo)準(zhǔn)的編譯器實(shí)現(xiàn),歸罪于平臺(tái)無關(guān)的系統(tǒng)級(jí)程序庫的缺少。

這些問題歸于一點(diǎn),就是缺乏一個(gè)卓越的廠商,能夠滿足整個(gè)C++社區(qū)的需求,勇于投入大量的資金開發(fā)必要的程序庫。

Lindholm: Java技術(shù)的成功,是因?yàn)樗诤线m的時(shí)間,出現(xiàn)在合適的地點(diǎn),而且合理地選擇了語言和計(jì)算平臺(tái)的支持目標(biāo)。Java并不是在所有場合都優(yōu)于其他OOP語 言,但是對(duì)于出現(xiàn)的新問題能夠解決得很出色。它面向Internet計(jì)算環(huán)境,避免了C++中晦澀的結(jié)構(gòu),成功翻越了繼承機(jī)制的惱人問題。垃圾收集機(jī)制顯 著地提高了生產(chǎn)率,降低了復(fù)雜度。在網(wǎng)絡(luò)背景下使用虛擬機(jī),以及有關(guān)安全性和動(dòng)態(tài)加載的一系列設(shè)計(jì)選擇,迎合了正在出現(xiàn)的需求和愿望。這些特性使Java 不僅成為現(xiàn)有程序員的新武器,而且也為新的程序員創(chuàng)造了繁榮的市場空間。

此外,Java擁有一個(gè)標(biāo)準(zhǔn)化的、二進(jìn)制形式的類庫,提供了必要的(當(dāng)然并非充分的)平臺(tái)與廠商無關(guān)性。平臺(tái)與廠商無關(guān)性要求一項(xiàng)技術(shù)必須有清晰的規(guī) 范,摒棄那些阻礙二進(jìn)制標(biāo)準(zhǔn)實(shí)施的特性。C++雖然有一個(gè)ISO標(biāo)準(zhǔn),但其實(shí)甚至對(duì)于相同系統(tǒng)與相同指令體系的各個(gè)平臺(tái),也提不出一個(gè)實(shí)用的、各版本兼容 的二進(jìn)制標(biāo)準(zhǔn)。

歷史上很多使用虛擬機(jī)的語言飽受責(zé)難,是因?yàn)槠洳粔虺錾男阅軉栴},而這要?dú)w過于緩慢的解釋器和糟糕的垃圾收集器。Java的早期實(shí)現(xiàn)也因?yàn)橥瑯拥膯?題受到嚴(yán)厲的批評(píng)。但是自那時(shí)起,業(yè)界向新的虛擬機(jī)實(shí)現(xiàn)技術(shù)投入了大量資金,取得了顯著的效果,如今在大部分場合,Java的性能跟常規(guī)的靜態(tài)編譯語言相 比毫不遜色。這使得程序員在獲得平臺(tái)

和廠商無關(guān)性的同時(shí),也不必付出性能上的代價(jià)。

C++并沒有強(qiáng)制使用面向?qū)ο蠓椒?,因此為了編寫出色的面向?qū)ο蟠a,就要求程序員們有相當(dāng)強(qiáng)的紀(jì)律性。很多公司就是因?yàn)檫@個(gè)原因放棄了C++。作為 語言,Java的一個(gè)突出的優(yōu)點(diǎn)就是強(qiáng)制面向?qū)ο蠓椒?,不允許非面向?qū)ο蟮慕Y(jié)構(gòu)。

C#介于C++和Java之間,腳踏兩只船,因此既不夠安全,又失之復(fù)雜。

對(duì)于公司來說,采用新的語言要付出巨大代價(jià)。雇不到好的程序員(沒人熟悉這種新語言),培訓(xùn)費(fèi)用高得驚人,學(xué)習(xí)過程中生產(chǎn)率和產(chǎn)品質(zhì)量下降,多年的經(jīng) 驗(yàn)隨風(fēng)消逝,等等。一種語言如何克服這些障礙?

Lindholm: 說得很對(duì),采用新東西確實(shí)常常開銷巨大。不過問題是:這個(gè)新東西是否能夠節(jié)省更多的開支,或者提供巨大的改進(jìn),獲取合理的回報(bào)?很多公司發(fā)現(xiàn),轉(zhuǎn)向 Java技術(shù)不論在開發(fā)的后端(盡快進(jìn)入市場、快速迭代開發(fā)、維護(hù)簡單性)還是前端(跨平臺(tái)發(fā)布,適用范圍從低端設(shè)備到高端服務(wù)器的技術(shù),安全性),都能 節(jié)省大筆的開銷。

對(duì)于新事物的接納,常常是在痛楚的壓力之下。很大程度上,這正是Java所經(jīng)歷的。Java的產(chǎn)生,是對(duì)當(dāng)時(shí)很多系統(tǒng)的缺陷所做出的反應(yīng)。Java技 術(shù)通過下面的手段減輕了開發(fā)者的痛楚:1) 顧及了網(wǎng)絡(luò)計(jì)算方面的需求,是應(yīng)運(yùn)而生。2) 在技術(shù)能力的抉擇上,保持良好的品位,顧及了大眾的心理。3) 采用適度強(qiáng)制性策略推行設(shè)計(jì)決定。此外,Java技術(shù)已經(jīng)成為大學(xué)教學(xué)中的主流,這同樣保證了Java開發(fā)者隊(duì)伍的不斷壯大。

但是最重要的一點(diǎn)是,再?zèng)]有另一種程序設(shè)計(jì)技術(shù),能夠像Java那樣允許程序員開發(fā)基于 Internet的不同平臺(tái)之上的應(yīng)用程序。Java平臺(tái)在這方面的杰出表現(xiàn),已經(jīng)被大量的實(shí)例證明。Java已經(jīng)成為Internet上的缺省應(yīng)用程序 平臺(tái),Java APIs也成為Internet應(yīng)用程序開發(fā)的天然平臺(tái)。

Stroustrup: 微軟和Sun把大筆的金錢扔在Java、VB和C#中,并不是因?yàn)樗夹陌l(fā)現(xiàn),也不是因?yàn)樗麄冋娴南嘈胚@些語言能夠帶給程序員更美好的生活,而是利益使 然。

有一個(gè)說法,認(rèn)為軟件工具廠商如果能夠把應(yīng)用程序開發(fā)者的專業(yè)技術(shù)任務(wù)負(fù)擔(dān)起來,將獲取巨大的經(jīng)濟(jì)利益。我對(duì)其背后的經(jīng)濟(jì)分析頗為懷疑,我認(rèn)為這很難 成為現(xiàn)實(shí),特別是當(dāng)應(yīng)用程序開發(fā)者使用開放的、標(biāo)準(zhǔn)化的工具時(shí),他們可以有多種選擇,從而使上面的想法更加不可能。

多年以前,C++就已經(jīng)具有泛型能力(也就是templates和STL),有運(yùn)算符重載,有枚舉類型?我們會(huì)不會(huì)在Java的未來版本中看到這些特 性?Java是不是應(yīng)該納入這些特性呢?

Strousturp:從1988-89年起,C++就已經(jīng)有了templates。但是我們花了不少時(shí)

間來了解如何最好地運(yùn)用這個(gè)工具,早期各廠家 對(duì)于template的支持在品質(zhì)上也有很大的差異。有些編譯器廠商動(dòng)作遲緩,至少有一個(gè)主要的編譯器廠商(好像是指微軟,微軟在Visual C++4.0才開始支持template,在此之前一直聲稱template是過于復(fù)雜而又沒什么用的技術(shù),時(shí)至今日,Visual C++對(duì)于template的支持在主流編譯器中都屬于最差的一檔——譯者注)暗中鼓勵(lì)聲名狼藉的反template宣傳,直到他們自己終于學(xué)會(huì)了這項(xiàng)技 術(shù)為止。直到今天,對(duì)于template的支持在品質(zhì)上仍然有待改進(jìn)。

你上面提到的那些特性,我認(rèn)為Java(還有C#)應(yīng)該,也肯定會(huì)逐漸引入。那些對(duì)于程序員來說最有用的語言特性和概念,將會(huì)逐漸集中,成為各家主流 語言的必然之選。也就是說,我認(rèn)為類似析構(gòu)函數(shù)和模板特殊化之類的機(jī)制,遠(yuǎn)遠(yuǎn)比枚舉等機(jī)制重要得多。

Lindholm:Java技術(shù)成功的原因之一,就是很清楚哪些不該做。我們得多問幾個(gè)為什么:這項(xiàng)特性是不是必不可少?增加它會(huì)帶來哪些開銷?運(yùn)算 符重載是C++中一項(xiàng)極其強(qiáng)大的特性,但是它也大大增加了C++語言的復(fù)雜度,很多人都難以招架。Java在各種可能的權(quán)衡之中,做出了明智的抉擇,找到 了能力與需求之間的完美平衡點(diǎn)。

當(dāng)然,Java也會(huì)發(fā)展,而且最重要的是,現(xiàn)在是開發(fā)者們?cè)谕苿?dòng)發(fā)展。Java增加泛型能力這件事,很好地展示了Java是如何通過整個(gè)開發(fā)者社群的 參與,在權(quán)衡中決定正確的平衡點(diǎn)。關(guān)于增加泛型類型(generic types)的“Java規(guī)格申請(qǐng)”(Java Specification Request, JSR)已經(jīng)進(jìn)入JCP(Java Community Process)程序,而且已經(jīng)開發(fā)了很長一段時(shí)間(參見 http://java.sun.com/aboutJava/communityprocess/之JSR-014)?,F(xiàn)在,在JCP中,有超過80個(gè) JSRs正在討論中,這充分體現(xiàn)了整個(gè)體系對(duì)開發(fā)者的積極反饋和高度合作,這正是驅(qū)動(dòng)Java平臺(tái)不斷進(jìn)化的動(dòng)力。

[編輯本段]

六、發(fā)展 vs. 革新

(Evolution vs. Revolution)

C++是一種發(fā)展型的語言,Java和C#似乎更像是革新型語言(它們是從頭設(shè)計(jì)的)?什么時(shí)候,革新型的語言才是必需的呢?

Lindholm: Java技術(shù)并非憑空出世,反而更像是發(fā)展型的。Java所有的特性,在Java平臺(tái)推出之前,都至少已經(jīng)存在于另一種環(huán)境之中。Java的貢獻(xiàn)在于,在 眾多的特性和權(quán)衡中,做出了合理的選擇,使得產(chǎn)品既實(shí)用,又優(yōu)雅。Java技術(shù)對(duì)于程序員的態(tài)度是:撫養(yǎng),但不溺愛。

Stroustrup:從技術(shù)上講,我并不認(rèn)為Java和C#是什么“從頭設(shè)計(jì)的”革新型語言。倘若Java是從技術(shù)原則出發(fā),從頭設(shè)計(jì),大概就不會(huì) 模仿C/C++那種丑陋和病態(tài)的語法了(不必驚訝,Stroustrup在很多場合表示過,C++采用C的語法形式,實(shí)在是迫于兼容性

。他本人更偏愛 Simula的語法——譯者)。

我認(rèn)為,只有當(dāng)程序員們面對(duì)的問題發(fā)生了根本的變化的時(shí)候,或者當(dāng)我們發(fā)現(xiàn)了全新的、極其優(yōu)越的程序設(shè)計(jì)技術(shù),又完全不能為現(xiàn)存語言所支持的時(shí)候,我 們才需要全新的語言。問題是,我們恐怕永遠(yuǎn)也碰不到那些“根本”、“全新”的情況。

我以為,自從OOP問世以來,可稱為“根本”的新型程序設(shè)計(jì)技術(shù),唯有泛型程序設(shè)計(jì)(generic programming)和生成式程序設(shè)計(jì)(generative programming)技術(shù),這兩項(xiàng)技術(shù)主要是源于C++ templates技術(shù)的運(yùn)用,也有一部分曾經(jīng)被視為面向?qū)ο蠛秃瘮?shù)式語言(functional languages)的次要成分,現(xiàn)在都變成正式、可用和可承受的技術(shù)了。我對(duì)于目前C++模板(template)程序設(shè)計(jì)的成果非常興奮。例如,像 POOMA, Blitz++和MTL等程序庫,在很多地方改變了數(shù)值計(jì)算的方式。

C#的一個(gè)“賣點(diǎn)”,就是它們的簡單性。現(xiàn)在Java是不是快失去這個(gè)賣點(diǎn)了?

Stroustrup:新語言總是宣稱自己如何如何簡單,對(duì)老語言的復(fù)雜性頗多非議。其實(shí)這種所謂的“簡單性”,簡單地說,就是不成熟性。語言的復(fù)雜 性,是在解決現(xiàn)實(shí)世界中極為煩瑣和特殊的復(fù)雜問題的過程中逐漸增加的。一個(gè)語言只要活的時(shí)間夠長,總會(huì)有某些地方逐漸復(fù)雜起來,或者是語言本身,或者是程 序庫和工具。C++和Java顯然都不例外,我看C#也一樣。如果一種語言能夠度過自己的幼年時(shí)代,它會(huì)發(fā)現(xiàn),自己無論是體積還是復(fù)雜性都大大增加了。

Lindholm:Java技術(shù)的的功能在增加,需要學(xué)習(xí)的東西也在增加。不過功能的增加并不一定帶來復(fù)雜性的增加。Java技術(shù)的發(fā)展,并沒有使學(xué) 習(xí)曲線更加陡峭,只是讓它繼續(xù)向右方延展了。

標(biāo)準(zhǔn)

標(biāo)準(zhǔn)化語言和開放型語言各自的優(yōu)點(diǎn)和缺點(diǎn)何在?

Lindholm:對(duì)于一個(gè)開放、不允許專有擴(kuò)展、具有權(quán)威的強(qiáng)制性標(biāo)準(zhǔn)語言或者運(yùn)行環(huán)境來說,不存在什么缺點(diǎn)。允許專有擴(kuò)展就意味著允許廠商下套子 綁架客戶。特別重要的是,必須讓整個(gè)平臺(tái),而不只是其中一部分完全標(biāo)準(zhǔn)化,才能杜絕廠商們利用高層次的專有API下套子??蛻粢笥羞x擇廠商的自由,他們 既要有創(chuàng)造性,又需要兼容性。

Stroustrup:對(duì)于一個(gè)語言,如C/C++來說,建立正式標(biāo)準(zhǔn)(如ISO標(biāo)準(zhǔn))最大的好處,在于可以防止某一個(gè)廠商操縱這種語言,把它當(dāng)成自 己的搖錢樹。多個(gè)廠商的競爭給用戶帶來的是較低的價(jià)位和較好的穩(wěn)定性。

專有語言的好處,一是流行,二是便宜(不過等你被套牢了之后,情況就會(huì)起變化),三是對(duì)于商業(yè)性需求可以做出快速的反應(yīng)。

標(biāo)準(zhǔn)化語言的特點(diǎn)之一是,它不能忽略特殊用戶的需求。比如我在AT&T中所考慮的

東西,其規(guī)模、可靠性和效率要求,跟那些普通廠商關(guān)注的大眾 軟件相比,根本不可同日而語。那些公司很自然只關(guān)注主要的需求。

然而,多數(shù)大機(jī)構(gòu)和身處前沿的公司,都有著特殊的需求。C++的設(shè)計(jì)是開放、靈活和高效的,能夠滿足我所能想象的任何需求。跟其他的現(xiàn)代語言相 比,C++的家長式作風(fēng)可謂少之又少,原因就在這。當(dāng)然,不能贊賞這一點(diǎn)的人會(huì)詬病C++的“危險(xiǎn)”。

擁有正式和開放標(biāo)準(zhǔn)的語言主要是為編程工具的使用者和客戶服務(wù)的,而擁有專屬“標(biāo)準(zhǔn)”的語言,主要是為廠商服務(wù)的。

OOD

面向?qū)ο笤O(shè)計(jì)(Object-Oriented Design,OOD)方法是OO方法中一個(gè)中間過渡環(huán)節(jié)。其主要作用是對(duì)OOA分析的結(jié)果作進(jìn)一步的規(guī)范化整理,以便能夠被OOP直接接受。

面向?qū)ο笤O(shè)計(jì)(OOD)是一種軟件設(shè)計(jì)方法,是一種工程化規(guī)范。這是毫無疑問的。按照Bjarne Stroustrup的說法,面向?qū)ο蟮木幊谭妒剑╬aradigm)是[Stroustrup, 97]:

l 決定你要的類;

l 給每個(gè)類提供完整的一組操作;

l 明確地使用繼承來表現(xiàn)共同點(diǎn)。

由這個(gè)定義,我們可以看出:OOD就是“根據(jù)需求決定所需的類、類的操作以及類之間關(guān)聯(lián)的過程”。

OOD的目標(biāo)是管理程序內(nèi)部各部分的相互依賴。為了達(dá)到這個(gè)目標(biāo),OOD要求將程序分成塊,每個(gè)塊的規(guī)模應(yīng)該小到可以管理的程度,然后分別將各個(gè)塊隱 藏在接口(interface)的后面,讓它們只通過接口相互交流。比如說,如果用OOD的方法來設(shè)計(jì)一個(gè)服務(wù)器-客戶端(client-server) 應(yīng)用,那么服務(wù)器和客戶端之間不應(yīng)該有直接的依賴,而是應(yīng)該讓服務(wù)器的接口和客戶端的接口相互依賴。

這種依賴關(guān)系的轉(zhuǎn)換使得系統(tǒng)的各部分具有了可復(fù)用性。還是拿上面那個(gè)例子來說,客戶端就不必依賴于特定的服務(wù)器,所以就可以復(fù)用到其他的環(huán)境下。如果 要復(fù)用某一個(gè)程序塊,只要實(shí)現(xiàn)必須的接口就行了。

OOD是一種解決軟件問題的設(shè)計(jì)范式(paradigm),一種抽象的范式。使用OOD這種設(shè)計(jì)范式,我們可以用對(duì)象(object)來表現(xiàn)問題領(lǐng)域 (problem domain)的實(shí)體,每個(gè)對(duì)象都有相應(yīng)的狀態(tài)和行為。我們剛才說到:OOD是一種抽象的范式。抽象可以分成很多層次,從非常概括的到非常特殊的都有,而 對(duì)象可能處于任何一個(gè)抽象層次上。另外,彼此不同但又互有關(guān)聯(lián)的對(duì)象可以共同構(gòu)成抽象:只要這些對(duì)象之間有相似性,就可以把它們當(dāng)成同一類的對(duì)象來處理。

一、OOD背景知識(shí)

計(jì)算機(jī)硬件技術(shù)卻在飛速發(fā)展。從幾十年前神秘的龐然大物,到現(xiàn)在隨身攜帶的移動(dòng)芯片;從每秒數(shù)千次運(yùn)算到每秒上百億次運(yùn)算。當(dāng)軟件開發(fā)者們還在尋找能 讓軟件開發(fā)生產(chǎn)力提

高一個(gè)數(shù)量級(jí)的“銀彈”[Brooks, 95]時(shí),硬件開發(fā)的生產(chǎn)力早已提升了百倍千倍。

硬件工程師們能夠如此高效,是因?yàn)樗麄兌己軕卸?。他們永遠(yuǎn)恪守“不要去重新發(fā)明輪子”的古訓(xùn)。Grady Booch把這些黑箱稱為類屬(class category),現(xiàn)在我們則通常把它們稱為“組件(component)”。

類屬是由被稱為類(class)的實(shí)體組成的,類與類之間通過關(guān)聯(lián)(relationship)結(jié)合在一起。一個(gè)類可以把大量的細(xì)節(jié)隱藏起來,只露出 一個(gè)簡單的接口,這正好符合人們喜歡抽象的心理。所以,這是一個(gè)非常偉大的概念,因?yàn)樗o我們提供了封裝和復(fù)用的基礎(chǔ),讓我們可以從問題的角度來看問題, 而不是從機(jī)器的角度來看問題。

軟件的復(fù)用最初是從函數(shù)庫和類庫開始的,這兩種復(fù)用形式實(shí)際上都是白箱復(fù)用。到90年代,開始有人開發(fā)并出售真正的黑箱軟件模塊:框架 (framework)和控件(control)??蚣芎涂丶€受平臺(tái)和語言的限制,現(xiàn)在軟件技術(shù)的新潮流是用SOAP作為傳輸介質(zhì)的Web Service,它可以使軟件模塊脫離平臺(tái)和語言的束縛,實(shí)現(xiàn)更高程度的復(fù)用。但是想一想,其實(shí)Web Service也是面向?qū)ο?,只不過是把類與類之間的關(guān)聯(lián)用XML來描述而已[Li, 02]。

在過去的十多年里,面向?qū)ο蠹夹g(shù)對(duì)軟件行業(yè)起到了極大的推動(dòng)作用。在可以預(yù)測(cè)的將來,它仍將是軟件設(shè)計(jì)的主要技術(shù)——至少我看不到有什么技術(shù)可以取代 它的。

二、OOD到底從哪兒來?

有很多人都認(rèn)為:OOD是對(duì)結(jié)構(gòu)化設(shè)計(jì)(Structured Design,SD)的擴(kuò)展,其實(shí)這是不對(duì)的。OOD的軟件設(shè)計(jì)觀念和SD完全不同。SD注重的是數(shù)據(jù)結(jié)構(gòu)和處理數(shù)據(jù)結(jié)構(gòu)的過程。而在OOD中,過程和數(shù) 據(jù)結(jié)構(gòu)都被對(duì)象隱藏起來,兩者幾乎是互不相關(guān)的。不過,追根溯源,OOD和SD有著非常深的淵源。

1967年前后,OOD和SD 的概念幾乎同時(shí)誕生,它們分別以不同的方式來表現(xiàn)數(shù)據(jù)結(jié)構(gòu)和算法。當(dāng)時(shí),圍繞著這兩個(gè)概念,很多科學(xué)家寫了大量的論文。其中,由Dijkstra和 Hoare兩人所寫的一些論文講到了“恰當(dāng)?shù)某绦蚩刂平Y(jié)構(gòu)”這個(gè)話題,聲稱goto語句是有害的,應(yīng)該用順序、循環(huán)、分支這三種控制結(jié)構(gòu)來構(gòu)成整個(gè)程序流 程。這些概念發(fā)展構(gòu)成了結(jié)構(gòu)化程序設(shè)計(jì)方法;而由Ole-Johan Dahl所寫的另一些論文則主要討論編程語言中的單位劃分,其中的一種程序單位就是類,它已經(jīng)擁有了面向?qū)ο蟪绦蛟O(shè)計(jì)的主要特征。

這兩種概念立刻就分道揚(yáng)鑣了。在結(jié)構(gòu)化這邊的歷史大家都很熟悉:NATO會(huì)議采納了 Dijkstra的思想,整個(gè)軟件產(chǎn)業(yè)都同意goto語句的確是有害的,結(jié)構(gòu)化方法、瀑布模型從70年代開始大行其道。同時(shí),無數(shù)的科學(xué)家和軟件工程師也 幫助結(jié)構(gòu)化方法不

斷發(fā)展完善,其中有很多今天足以使我們振聾發(fā)聵的名字,例如Constantine、Yourdon、DeMarco和 Dijkstra。有很長一段時(shí)間,整個(gè)世界都相信:結(jié)構(gòu)化方法就是拯救軟件工業(yè)的 “銀彈”。當(dāng)然,時(shí)間最后證明了一切。

而此時(shí),面向?qū)ο髣t在研究和教育領(lǐng)域緩慢發(fā)展。結(jié)構(gòu)化程序設(shè)計(jì)幾乎可以應(yīng)用于任何編程語言之上,而面向?qū)ο蟪绦蛟O(shè)計(jì)則需要語言的支持[1],這也妨礙 了面向?qū)ο蠹夹g(shù)的發(fā)展。實(shí)際上,在60年代后期,支持面向?qū)ο筇匦缘恼Z言只有Simula-67 這一種。到70年代,施樂帕洛阿爾托研究中心(PARC)的 Alan Key等人又發(fā)明了另一種基于面向?qū)ο蠓椒ǖ恼Z言,那就是大名鼎鼎的Smalltalk。但是,直到80年代中期,Smalltalk和另外幾種面向?qū)ο?語言仍然只停留在實(shí)驗(yàn)室里。

到90年代,OOD突然就風(fēng)靡了整個(gè)軟件行業(yè),這絕對(duì)是軟件開發(fā)史上的一次革命。不過,登高才能望遠(yuǎn),新事物總是站在舊事物的基礎(chǔ)之上的。70年代和 80年代的設(shè)計(jì)方法揭示出許多有價(jià)值的概念,誰都不能也不敢忽視它們,OOD也一樣。

三、OOD和傳統(tǒng)方法有什么區(qū)別?

還記得結(jié)構(gòu)化設(shè)計(jì)方法嗎?程序被劃分成許多個(gè)模塊,這些模塊被組織成一個(gè)樹型結(jié)構(gòu)。這棵樹的根就是主模塊,葉子就是工具模塊和最低級(jí)的功能模塊。同 時(shí),這棵樹也表示調(diào)用結(jié)構(gòu):每個(gè)模塊都調(diào)用自己的直接下級(jí)模塊,并被自己的直接上級(jí)模塊調(diào)用。

那么,哪個(gè)模塊負(fù)責(zé)收集應(yīng)用程序最重要的那些策略?當(dāng)然是最頂端的那些。在底下的那些模塊只管實(shí)現(xiàn)最小的細(xì)節(jié),最頂端的模塊關(guān)心規(guī)模最大的問題。所 以,在這個(gè)體系結(jié)構(gòu)中越靠上,概念的抽象層次就越高,也越接近問題領(lǐng)域;體系結(jié)構(gòu)中位置越低,概念就越接近細(xì)節(jié),與問題領(lǐng)域的關(guān)系就越少,而與解決方案領(lǐng) 域的關(guān)系就越多。

但是,由于上方的模塊需要調(diào)用下方的模塊,所以這些上方的模塊就依賴于下方的細(xì)節(jié)。換句話說,與問題領(lǐng)域相關(guān)的抽象要依賴于與問題領(lǐng)域無關(guān)的細(xì)節(jié)!這 也就是說,當(dāng)實(shí)現(xiàn)細(xì)節(jié)發(fā)生變化時(shí),抽象也會(huì)受到影響。而且,如果我們想復(fù)用某一個(gè)抽象的話,就必須把它依賴的細(xì)節(jié)都一起拖過去。

而在OOD中,我們希望倒轉(zhuǎn)這種依賴關(guān)系:我們創(chuàng)建的抽象不依賴于任何細(xì)節(jié),而細(xì)節(jié)則高度依賴于上面的抽象。這種依賴關(guān)系的倒轉(zhuǎn)正是OOD和傳統(tǒng)技術(shù) 之間根本的差異,也正是OOD思想的精華所在。

四、OOD步驟

細(xì)化重組類

細(xì)化和實(shí)現(xiàn)類間關(guān)系,明確其可見性

增加屬性,指定屬性的類型與可見性

分配職責(zé),定義執(zhí)行每個(gè)職責(zé)的方法

對(duì)消息驅(qū)動(dòng)的系統(tǒng),明確消息傳遞方式

利用設(shè)計(jì)模式進(jìn)行局部設(shè)計(jì)

畫出詳細(xì)的類圖與時(shí)序圖

五、OOD設(shè)計(jì)過程中要展開的主要幾項(xiàng)工作

(一)對(duì)象定義規(guī)格的求精過程

對(duì)于OOA所抽象出來的對(duì)象-&-類以及匯集的分析文檔,OOD需要有一個(gè)根據(jù)設(shè)計(jì)要求整理和求精的過程,使之更能符合OOP的需要。這個(gè)整理和求精 過程主要有兩個(gè)方面:一是要根據(jù)面向?qū)ο蟮母拍?/p>

模型整理分析所確定的對(duì)象結(jié)構(gòu)、屬性、方法等內(nèi)容,改正錯(cuò)誤的內(nèi)容,刪去不必要和重復(fù)的內(nèi)容等。二是進(jìn)行分類整理,以便于下一步數(shù)據(jù)庫設(shè)計(jì)和程序處理 模塊設(shè)計(jì)的需要。整理的方法主要是進(jìn)行歸

類,對(duì)類一&一對(duì)象、屬性、方法和結(jié)構(gòu)、主題進(jìn)行歸類。

(二)數(shù)據(jù)模型和數(shù)據(jù)庫設(shè)計(jì)

數(shù)據(jù)模型的設(shè)計(jì)需要確定類-&-對(duì)象屬性的內(nèi)容、消息連接的方式、系統(tǒng)訪問、數(shù)據(jù)模型的方法等。最后每個(gè)對(duì)象實(shí)例的數(shù)據(jù)都必須落實(shí)到面向?qū)ο蟮膸旖Y(jié)構(gòu) 模型中。

(三)優(yōu)化

OOD的優(yōu)化設(shè)計(jì)過程是從另一個(gè)角度對(duì)分析結(jié)果和處理業(yè)務(wù)過程的整理歸納,優(yōu)化包括對(duì)象和結(jié)構(gòu)的優(yōu)化、抽象、集成。

對(duì)象和結(jié)構(gòu)的模塊化表示OOD提供了一種范式,這種范式支持對(duì)類和結(jié)構(gòu)的模塊化。這種模塊符合一般模塊化所要求的所有特點(diǎn),如信息隱蔽性好,內(nèi)部聚合 度強(qiáng)和模塊之間耦合度弱等。

集成化使得單個(gè)構(gòu)件有機(jī)地結(jié)合在一起,相互支持。

六、OO方法的特點(diǎn)和面臨的問題

OO方法以對(duì)象為基礎(chǔ),利用特定的軟件工具直接完成從對(duì)象客體的描述到軟件結(jié)構(gòu)之間的轉(zhuǎn)換。這是OO方法最主要的特點(diǎn)和成就。OO方法的應(yīng)用解決了傳 統(tǒng)結(jié)構(gòu)化開發(fā)方法中客觀世界描述工具與軟

件結(jié)構(gòu)的不一致性問題,縮短了開發(fā)周期,解決了從分析和設(shè)計(jì)到軟件模塊結(jié)構(gòu)之間多次轉(zhuǎn)換映射的繁雜過程,是一種很有發(fā)展前途的系統(tǒng)開發(fā)方法。

但是同原型方法一樣,OO方法需要一定的軟件基礎(chǔ)支持才可以應(yīng)用,另外在大型的MIS開發(fā)中如果不經(jīng)自頂向下的整體劃分,而是一開始就自底向上的采用 OO 方法開發(fā)系統(tǒng),同樣也會(huì)造成系統(tǒng)結(jié)構(gòu)不合理、各部分關(guān)系失調(diào)等問題。所以O(shè)O方法和結(jié)構(gòu)化方法目前仍是兩種在系統(tǒng)開發(fā)領(lǐng)域相互依存的、不可替代的方法。

七、OOD能給我?guī)硎裁矗?/b>

問這個(gè)問題的人,腦子里通常是在想“OOD能解決所有的設(shè)計(jì)問題嗎?”沒有銀彈。OOD也不是解決一切設(shè)計(jì)問題、避免軟件危機(jī)、捍衛(wèi)世界和平……的銀 彈。OOD只是一種技術(shù)。但是,它是一種優(yōu)秀的技術(shù),它可以很好地解決目前的大多數(shù)軟件設(shè)計(jì)問題 ——當(dāng)然,這要求設(shè)計(jì)者有足夠的能力。

OOD可能會(huì)讓你頭疼,因?yàn)橐獙W(xué)會(huì)它、掌握它是很困難的;OOD甚至?xí)屇闶?,因?yàn)樗膊⒉怀墒臁⒉⒉煌昝?。OOD也會(huì)給你帶來欣喜,它讓你可以專 注于設(shè)計(jì),而不必

操心那些細(xì)枝末節(jié);OOD也會(huì)使你成為一個(gè)更好的設(shè)計(jì)師,它能提供給你很好的工具,讓你能開發(fā)出更堅(jiān)固、更可維護(hù)、更可復(fù)用的軟件。

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時(shí)請(qǐng)結(jié)合常識(shí)與多方信息審慎甄別。
平臺(tái)聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點(diǎn),簡書系信息發(fā)布平臺(tái),僅提供信息存儲(chǔ)服務(wù)。

相關(guān)閱讀更多精彩內(nèi)容

  • 1. Java基礎(chǔ)部分 基礎(chǔ)部分的順序:基本語法,類相關(guān)的語法,內(nèi)部類的語法,繼承相關(guān)的語法,異常的語法,線程的語...
    子非魚_t_閱讀 34,823評(píng)論 18 399
  • Android 自定義View的各種姿勢(shì)1 Activity的顯示之ViewRootImpl詳解 Activity...
    passiontim閱讀 179,323評(píng)論 25 708
  • 面向?qū)ο蟪绦蛟O(shè)計(jì)(英語:Object-oriented programming,縮寫:OOP)是種具有對(duì)象概念的程...
    逆風(fēng)飛行1226閱讀 1,363評(píng)論 0 5
  • 從三月份找實(shí)習(xí)到現(xiàn)在,面了一些公司,掛了不少,但最終還是拿到小米、百度、阿里、京東、新浪、CVTE、樂視家的研發(fā)崗...
    時(shí)芥藍(lán)閱讀 42,872評(píng)論 11 349
  • 也許在這個(gè)世上我們很難找到真正屬于自己的另一個(gè)世界了吧。 從博客、微博、微信朋友圈,一路走來,你會(huì)發(fā)現(xiàn)屬于自己的單...
    iMe心理閱讀 224評(píng)論 0 0

友情鏈接更多精彩內(nèi)容