2014年8月,我應(yīng)內(nèi)訓(xùn)經(jīng)理的要求灭贷,做一次技術(shù)分享温学。我認為在公司的IT開發(fā)中,對面向?qū)ο蟮脑O(shè)計和實現(xiàn)沒有得到足夠的重視甚疟,宣貫做的不夠仗岖,大部分軟件工程師在這方面的素養(yǎng)也有待提高。另外由于我的專業(yè)和長時間的實踐览妖,始終想對面向?qū)ο笤O(shè)計做一個自己的闡述轧拄。我覺得這是特別好的一次機會,所以就這個問題做了題為《動機讽膏、原則與模式——OO設(shè)計之我見》的講座紧帕,反響較好。這篇文章就是脫胎于這次分享,并在文字上更規(guī)范了一些是嗜。
編程是什么愈案?
說到面向?qū)ο蟮脑O(shè)計和開發(fā),我就想到上學(xué)的時候Pascal老師問過的問題:編程是什么鹅搪?經(jīng)過這么多年的實踐站绪,我覺得當時老師給出的答案是本質(zhì)上的。編程就是數(shù)據(jù)結(jié)構(gòu)加算法丽柿。這里先談?wù)勎覍λ惴ǖ睦斫狻?/p>
算法就是解決問題的步驟恢准,我認為是一種對軟件工程的動態(tài)表述。關(guān)于算法甫题,我有一個好消息和一個壞消息馁筐。好消息是,作為社會科學(xué)的范疇坠非,大到國家強盛敏沉,民族復(fù)興,小到家庭和諧炎码,自我實現(xiàn)盟迟。往往都很難用1234的步驟來描述;而作為自然科學(xué)的計算機技術(shù)潦闲,大多數(shù)的問題都可以用某種算法的表述十分精確的定義攒菠。這就是為什么讓我們覺得科學(xué)家比社會學(xué)家更靠譜;壞消息是即使有明確的步驟歉闰,很多算法還是很難辖众。探其緣由,算法的難度來源于與數(shù)學(xué)的不解之緣和敬。因為很多算法問題都是可以通過數(shù)學(xué)來進行建模凹炸,進而變成一個數(shù)學(xué)問題來求解。
討論完算法概龄,再說數(shù)據(jù)結(jié)構(gòu)还惠,數(shù)據(jù)結(jié)構(gòu)是數(shù)據(jù)的組織方式饲握,是軟件工程的靜態(tài)表述私杜,數(shù)據(jù)結(jié)構(gòu)是一種靜態(tài)的美。作為一個普通的程序員救欧,你可能不會設(shè)計很高深的算法衰粹,但你會經(jīng)常遇到設(shè)計數(shù)據(jù)結(jié)構(gòu)的問題,OO設(shè)計笆怠,本質(zhì)上就是設(shè)計數(shù)據(jù)結(jié)構(gòu)铝耻。從現(xiàn)在業(yè)界的技術(shù)人員構(gòu)成,你會發(fā)現(xiàn),真正研究狹義的算法的程序員是金字塔的塔尖瓢捉,他們在大型科研單位和BAT這種巨型互聯(lián)網(wǎng)企業(yè)中频丘。而大量的軟件工程師和高級軟件工程師其實都在做數(shù)據(jù)結(jié)構(gòu),只是在解決數(shù)據(jù)結(jié)構(gòu)問題的過程中泡态,涉及解決問題的步驟搂漠,即廣義的算法。而且好的數(shù)據(jù)結(jié)構(gòu)設(shè)計某弦,會從根本上簡化解決問題的步驟桐汤。
程序員的境界
我在這里提到了兩個典型的員工,他們可能不是具體的兩個人靶壮,但絕對代表了兩類人怔毛。老李,10年以上工齡的老程序員腾降,習(xí)慣了開發(fā)過程中不費腦子的Ctrl+c,v大法拣度,鮮有拿得出手的OO設(shè)計方案;小王蜂莉,科班出身但經(jīng)驗缺乏蜡娶,遇到問題善于思考和總結(jié),即使很小的設(shè)計映穗,也能看出OO設(shè)計的影子窖张。我對他們的看法是,老李是典型的“一年進步蚁滋,N年循環(huán)”的程序員宿接,而小王終將“從優(yōu)秀到卓越”。為什么造成了這種不同辕录?境界的不同睦霎!
這時我又想起了《大腕》這部電影,其中一個橋段就是葛優(yōu)給Lucy講解境界的含義走诞。它是一種眼光副女,境界越高的人,看的就越遠蚣旱。我給出了這樣一張slide和一個結(jié)論碑幅。就OO設(shè)計而言,普通的程序員塞绿,優(yōu)秀的程序員沟涨,偉大的程序員和佛,境界就是這么大的區(qū)別异吻,而在我們修煉內(nèi)功的道路上裹赴,提升OO設(shè)計能力,就是提升境界。
動機棋返、原則與模式
我認為延都,軟件設(shè)計可以分為三個重要的層次,面向?qū)ο蟮乃枷牒蛙浖?gòu)件)復(fù)用的動機是最高層次的睛竣,面向?qū)ο蟮脑O(shè)計原則是對以上內(nèi)容的具體化和銜接窄潭,而設(shè)計模式才是更具體到實際問題的解決方案,即接”地氣“的部分酵颁。所以一個好的軟件系統(tǒng)設(shè)計師嫉你,首先應(yīng)該有面向?qū)ο蟮乃枷耄缓笳莆彰嫦驅(qū)ο蟮脑O(shè)計原則躏惋,最后才是具體問題具體分析幽污,應(yīng)用模式來解決實際問題。這樣才會設(shè)計出比較合理的系統(tǒng)簿姨,以及降低濫用和錯用設(shè)計模式的幾率距误。
動機是指一個人想要干某件事情而在心里上形成的思維途徑。同時也是一個人在做某種決定所產(chǎn)生的念頭扁位。說到動機准潭,可以比較兩種程序員,分別是懶程序員和“懶”程序員域仇。前者刑然,不深入思考系統(tǒng)的結(jié)構(gòu),不會用面向?qū)ο蟮姆椒ㄔO(shè)計整個系統(tǒng)暇务,停留在面向過程的思維模式泼掠,簡單的復(fù)制粘貼;后者垦细,不是真的懶择镇,而是不愿意在后期維護更多的代碼,愿意在設(shè)計階段投入更多的精力括改,專注于解耦和封裝腻豌,磨刀不誤砍柴工。
我把真正的OO設(shè)計的動機總結(jié)為三點嘱能,首先是真實的反應(yīng)客觀世界吝梅,也就是建立模型;其次是把正確的算法焰檩,即解決問題的步驟放到正確的結(jié)構(gòu)中憔涉;最后是擁抱變化订框,為產(chǎn)品析苫,也為自己的未來考慮。
有些人認為,學(xué)習(xí)OO設(shè)計就是學(xué)習(xí)設(shè)計模式衩侥。但我更認為国旷,OO設(shè)計的原則重于設(shè)計模式∶K溃《Java與模式》是一部描述設(shè)計模式的出了名的大部頭跪但,一共1024頁(好有計算機科學(xué)的感覺)。盡管你可以想象他用超過90%的篇幅描述各種設(shè)計模式峦萎,但是你可能不會想到屡久,他在第二部分就寫了這么一段話:
在目前的軟件界,學(xué)習(xí)和應(yīng)用設(shè)計模式正在形成風(fēng)氣爱榔。的確被环,通過學(xué)習(xí)和應(yīng)用設(shè)計模式,可以更加深入地理解面向?qū)ο蟮脑O(shè)計理念详幽,從而幫助設(shè)計師改善自己的系統(tǒng)設(shè)計筛欢。但是,設(shè)計模式并不能提供具有普遍性的設(shè)計指導(dǎo)原則唇聘。在讀者經(jīng)過一段時間的對設(shè)計模式的學(xué)習(xí)和使用之后版姑,就會覺得這些孤立的設(shè)計模式的背后應(yīng)當還有一些更為深層的、更具有普遍性的迟郎、共同的思想原則剥险。
可見本書的作者,希望讀者在進入設(shè)計模式這個絢麗世界前宪肖,先要掌握OO設(shè)計原則這個指南針炒嘲,才不會在隨后的學(xué)習(xí)中迷失方向,才能掌握“大巧若拙匈庭,大辯若訥”的OO設(shè)計精髓夫凸。那么OO設(shè)計原則都有哪些呢?我又怎樣對它們進行解讀呢阱持?請看本文章的第二部分夭拌。