創建高質量的代碼_3(讀書筆記)

高質量的子程序

在討論高質量的子程序的細節之前,明確下面這兩個基本術語會很有幫助。首先,什么是“子程序(routine)”? 子程序是為實現一個特定的目的而編寫的一個可被調用的方法(method)或過程(procedure)。

拋開計算機本身,子程序也算得上是計算機科學中一項最重大的發明了。子程序的使用使得程序變得更加易讀,更易于理解,比在任何編程語言的任何功能特性都更容易。

子程序也是迄今為止發明出來的用以節約空間和提高性能的最重要手段。

3.1 ?創建子程序的正當理由

下面概況了創建子程序的一些理由

- ?降低復雜度;

- ?引入中間的、易懂從抽象;

- ?避免代碼代碼重復;

- ?支持子類化;

- ?隱藏順序;

- ?隱藏指針操作;

- ?提高可移植性;

- ?簡化復雜的邏輯判斷;

- ?改善性能;

除此之外,創建類的很多理由也是創建子程序的理由:

- ?隔離復雜度;

- ?隱藏實現細節;

- ?限制變化所帶來的影響;

- ?隱藏全局數據;

- ?形成中央控制點;

- ?促成可重用的代碼;

- ?達到特定的重構目的;


3.2 ?在子程序層上設計

首先來理解一個概念,內聚性。對子程序而言,內聚性是指子程序中各種操作之間聯系的緊密程度。我們的目標是讓每一個子程序只把一件事情做好,不再做任何其他事情。這樣做的好處是得到更高的可靠性。

關于內聚性的討論一般會涉及到內聚性的幾個層次。理解一些概念要比記住一些特定的術語更重要。這些概念可以幫助你思考如何讓子程序盡可能地內聚。

功能的內聚性:是最強也是最好的一種內聚性,也就是說讓一個子程序僅執行一項操作。

當然,以這種方式來評估內聚性,前提是子程序所執行的操作與其名字相符——如果它還做了其他的操作,那么它就不夠內聚,同時其命名也有問題。

除此之外,還有其他一些種類的內聚性人們卻通常認為是不夠理想的。比如:順序上的內聚性、通信上的內聚性、臨時的內聚性。

為了得到更好的內聚性,可以把不同的操作納入各自的子程序中。讓調用方的子程序具有單一而完整的功能。為了讓所有的子程序都具有功能上的內聚性,對兩個或更多的原有子程序進行修改是很常見的。

這些術語中沒有哪個是神秘的或者圣神不可侵犯的。需要理解的是其中的想法,而不是那些術語。編寫具有功能上的內聚性的子程序幾乎總是可能的,因此把注意力集中于功能上的內聚性,從而得到最大的收獲。


3.3 ?好的子程序名字

好的子程序名字能清晰地描述子程序所做的一切。這里是有效地給子程序命名的一些指導原則。

- 描述子程序所做的所有事情;

- 避免使用無意義的、模糊或表述不清的動詞;

- 不要僅通過數字來形成不同的子程序名字;

- 根據需要確定子程序名字的長度;

- ?給函數命名時要返回值有所描述

- 給過程起名時使用語氣強烈的動詞加賓語的形式;

- 準確使用對仗詞;

- 為常用操作確立命名規則。

3.4 ?如何使用子程序參數

- ?按照輸入-修改-輸出的順序排列參數。不要隨機地或按字母順序排列參數,而應該先列出僅作為輸入用途的參數,然后是既作為輸入又作為輸出用途的參數,最后才是僅作為輸出用途的參數。這種排列方法暗含了子程序的內部操作所發生的順序——先是輸入數據,然后修改數據,最后輸出結果。

- 如果幾個子程序都用了類似的一些參數,應該讓這些參數的排列順序保持一致。

- 使用所有的參數。

- 把狀態或出錯變量放在最后。按照習慣做法,狀態變量和那些用于指示發生錯誤的變量應該放在參數表的最后。它們只是附屬于程序的主要功能,而且它們是僅用于輸出的參數,因此這是一種很有道理的規則。

- 不要把子程序的參數用做工作變量。把傳入子程序的參數用做工作變量是很危險的。應該使用局部變量。

- 在接口中對參數的假定加以說明。如果你假定了傳遞給子程序的參數具有某種特征,那就要對這種假定加以說明。在子程序內部和調用子程序的地方同時對所做的假定進行說是值得的。不要等到把子程序寫完了之后再回過頭去寫注釋——你是不會記住所有這些假定的。一種比用注釋還好的方法,是在代碼中使用斷言(assertions)。

應該對這些接口參數的假定進行說明:參數是僅用于輸入的、要被修改的、還是僅用于輸出的;表示數量的參數的單位;如果沒有枚舉類型的話,應該說明狀態代碼和錯誤值的含義;所能接受的數值的范圍;不該出現的特定數值。

- 把子程序的參數個數限制在大約7個以內。在實踐中,子程序中參數的個數到底應該限制在多少,取決于你所使用的編程語言如何支持復雜的數據類型。如果你使用的是一種支持結構化數據的現代編程語言,你就可以傳遞一個含有13個成員的合成數據類型,并將它看作一個大數據塊。如果你使用的是一種更為原始的編程語言,那你可能需要分別傳遞全部13個成員。

如果你發現自己一直需要傳遞很多參數,這就說明子程序之間的耦合太過緊密了。應該重新設計這個或這組子程序,降低其間的耦合度。如果你向很多不同的子程序傳遞相同的數據,就請把這些子程序組成一個類,并把那些經常使用的數據用作類的內部數據。

- 考慮對參數采用某種表示輸入、修改、輸出的命名規則。

- 為子程序傳遞用以維持其接口抽象的變量或對象。

- 確保實際參數與形式參數相匹配。



核對表: ?高質量的子程序

大局事項

- ?創建子程序的理由充分嗎?

- ?一個子程序中所有適于單獨提出的部分是不是已經被提出到單獨的子程序中了?

- ?過程的名字中是否用了強烈、清晰的“動詞+賓語”詞組?函數的名字是否描述了其返回值?

- ?子程序的名字是否描述了它所做的全部事情?

- ?是否給常用的操作建立了命名規則?

- ?子程序是否具有強烈的功能上的內聚性?即它是否做且只做一件事情,并且把它做得很好?

- ?子程序之間是否有較松的耦合?子程序與其他子程序之間的連接是否是小的、明確的、可見的和靈活的?

- ?子程序的長度是否是由其功能和邏輯自熱確定,而非遵循任何人為的編碼標準?

參數傳遞適宜

- ?整體來看,子程序的參數表是否表現出一種具有整體性且一致的接口抽象?

- ?子程序參數的排列順序是否合理?是否與類似的子程序的參數排列順序相符?

- ?接口假定是否已在文檔中說明?

- ?子程序的參數個數是否沒超過7個?

- ?是否用到了每一個輸入參數?是否用到了每一個輸出參數?

- ?子程序是否避免了把輸入參數用做工作變量?

- ?如果子程序是一個函數,那么它是否在所有可能的情況下都能返回一個合法的值?

要點

- ?創建子程序最主要的目的是提高程序的可管理性,當然也有其他一些好的理由。其中,節省代碼空間只是一個次要的原因;提高可讀性、可靠性和可修改性等原因都更重一些。

- ?有時候,把一些簡單的操作寫成獨立的子程序也非常有價值。

- ?子程序可以按照其內聚性分為很多類,而你應該讓大多數子程序具有功能上的內聚性,這是最佳的一種內聚性。

- ?子程序的名字是它的質量的指示器。如果名字糟糕但恰如其分,那就說明這個子程序設計得很差勁。如果名字糟糕且又不準確,那么它就反映不出程序是干什么的。不管怎樣,糟糕的名字都意味著程序需要修改。

- ?只有在某個子程序的主要目的是返回有其名字所描述的特定結果時,才應該使用函數。

- ?細心的程序員會非常謹慎地使用宏,而且只在萬不得已時才用。

最后編輯于
?著作權歸作者所有,轉載或內容合作請聯系作者
平臺聲明:文章內容(如有圖片或視頻亦包括在內)由作者上傳并發布,文章內容僅代表作者本人觀點,簡書系信息發布平臺,僅提供信息存儲服務。
  • 序言:七十年代末,一起剝皮案震驚了整個濱河市,隨后出現的幾起案子,更是在濱河造成了極大的恐慌,老刑警劉巖,帶你破解...
    沈念sama閱讀 228,156評論 6 531
  • 序言:濱河連續發生了三起死亡事件,死亡現場離奇詭異,居然都是意外死亡,警方通過查閱死者的電腦和手機,發現死者居然都...
    沈念sama閱讀 98,401評論 3 415
  • 文/潘曉璐 我一進店門,熙熙樓的掌柜王于貴愁眉苦臉地迎上來,“玉大人,你說我怎么就攤上這事。” “怎么了?”我有些...
    開封第一講書人閱讀 176,069評論 0 373
  • 文/不壞的土叔 我叫張陵,是天一觀的道長。 經常有香客問我,道長,這世上最難降的妖魔是什么? 我笑而不...
    開封第一講書人閱讀 62,873評論 1 309
  • 正文 為了忘掉前任,我火速辦了婚禮,結果婚禮上,老公的妹妹穿的比我還像新娘。我一直安慰自己,他們只是感情好,可當我...
    茶點故事閱讀 71,635評論 6 408
  • 文/花漫 我一把揭開白布。 她就那樣靜靜地躺著,像睡著了一般。 火紅的嫁衣襯著肌膚如雪。 梳的紋絲不亂的頭發上,一...
    開封第一講書人閱讀 55,128評論 1 323
  • 那天,我揣著相機與錄音,去河邊找鬼。 笑死,一個胖子當著我的面吹牛,可吹牛的內容都是我干的。 我是一名探鬼主播,決...
    沈念sama閱讀 43,203評論 3 441
  • 文/蒼蘭香墨 我猛地睜開眼,長吁一口氣:“原來是場噩夢啊……” “哼!你這毒婦竟也來了?” 一聲冷哼從身側響起,我...
    開封第一講書人閱讀 42,365評論 0 288
  • 序言:老撾萬榮一對情侶失蹤,失蹤者是張志新(化名)和其女友劉穎,沒想到半個月后,有當地人在樹林里發現了一具尸體,經...
    沈念sama閱讀 48,881評論 1 334
  • 正文 獨居荒郊野嶺守林人離奇死亡,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內容為張勛視角 年9月15日...
    茶點故事閱讀 40,733評論 3 354
  • 正文 我和宋清朗相戀三年,在試婚紗的時候發現自己被綠了。 大學時的朋友給我發了我未婚夫和他白月光在一起吃飯的照片。...
    茶點故事閱讀 42,935評論 1 369
  • 序言:一個原本活蹦亂跳的男人離奇死亡,死狀恐怖,靈堂內的尸體忽然破棺而出,到底是詐尸還是另有隱情,我是刑警寧澤,帶...
    沈念sama閱讀 38,475評論 5 358
  • 正文 年R本政府宣布,位于F島的核電站,受9級特大地震影響,放射性物質發生泄漏。R本人自食惡果不足惜,卻給世界環境...
    茶點故事閱讀 44,172評論 3 347
  • 文/蒙蒙 一、第九天 我趴在偏房一處隱蔽的房頂上張望。 院中可真熱鬧,春花似錦、人聲如沸。這莊子的主人今日做“春日...
    開封第一講書人閱讀 34,582評論 0 26
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽。三九已至,卻和暖如春,著一層夾襖步出監牢的瞬間,已是汗流浹背。 一陣腳步聲響...
    開封第一講書人閱讀 35,821評論 1 282
  • 我被黑心中介騙來泰國打工, 沒想到剛下飛機就差點兒被人妖公主榨干…… 1. 我叫王不留,地道東北人。 一個月前我還...
    沈念sama閱讀 51,595評論 3 390
  • 正文 我出身青樓,卻偏偏與公主長得像,于是被迫代替她去往敵國和親。 傳聞我的和親對象是個殘疾皇子,可洞房花燭夜當晚...
    茶點故事閱讀 47,908評論 2 372

推薦閱讀更多精彩內容

  • 第一部分 打好基礎 Laying the Foundation 第一章 歡迎進入軟件構建的世界 Welcome t...
    白樺葉閱讀 4,655評論 0 17
  • Spring Cloud為開發人員提供了快速構建分布式系統中一些常見模式的工具(例如配置管理,服務發現,斷路器,智...
    卡卡羅2017閱讀 134,781評論 18 139
  • 本文將從變量,語句,代碼塊,子程序,到類以及框架設計,詳細描述了如何編寫高質量的程序。盡管大部分原則你可能都知道了...
    動感小前端閱讀 2,107評論 6 28
  • 軟件構件中的設計 設計中的挑戰 “軟件設計”一詞意味著去構思、創造或者發明一套方案,把一份計算機軟件的規格說...
    9d710097e616閱讀 546評論 0 0
  • 心有所系時,夢中猶在;望穿秋水兮,白黑如一,奈何心有萬千結。結不解,心難脫,何日臥石環翠墨?半杯茶香半杯醉,竹門半...
    琢濯閱讀 227評論 0 2