注重实效的程序员
1、關(guān)心你的技藝?
Care About Your Craft?
除非你在乎能否漂亮地開(kāi)發(fā)出軟件,否則其它事情都是沒(méi)有意義的。
2、思考!你的工作?
Think!About Your Work?
在你做某件事情的時(shí)候思考你在做什么。不間斷地思考,實(shí)時(shí)地批判你的工作。這將占據(jù)你的一些寶貴時(shí)間,酬勞則是更為活躍地參與你喜愛(ài)的工作、感覺(jué)到自己在掌握范圍日增的各種主題以及因感受到持續(xù)的進(jìn)步而歡愉。從長(zhǎng)遠(yuǎn)來(lái)說(shuō),你在時(shí)間上的投入將會(huì)隨著你和你的團(tuán)隊(duì)變得更為高效、編寫出更易于維護(hù)的代碼以及開(kāi)會(huì)時(shí)間的減少而得到回報(bào)。?
3、提供各種選擇,不要找蹩腳的借口?
Provide Options,Don't Make Lame Excuses?
不要說(shuō)事情做不到;要說(shuō)明能夠做什么來(lái)挽回局面。不要害怕提出要求,也不要害怕承認(rèn)你需要幫助。
4、不要容忍破窗戶?
Don't Live With Broken Windows?
不要留著“破窗戶”(低劣的設(shè)計(jì)、錯(cuò)誤的決策、或者糟糕的代碼)不修。發(fā)現(xiàn)一個(gè)就修一個(gè)。如果沒(méi)有足夠的時(shí)間進(jìn)行適當(dāng)?shù)男蘩?#xff0c;采取某種行動(dòng)防止進(jìn)一步的破壞,并說(shuō)明情勢(shì)處在你的控制之下。?
如果你發(fā)現(xiàn)你所在團(tuán)隊(duì)和項(xiàng)目的代碼十分漂亮——編寫整潔、設(shè)計(jì)良好,并且很優(yōu)雅,你不會(huì)想成為第一個(gè)弄臟東西的人。
5、做變化的催化劑?
Be a Catalyst for Change?
你不能強(qiáng)迫人們改變。相反,要向他們展示未來(lái)可能會(huì)怎樣,并幫助他們參與對(duì)未來(lái)的創(chuàng)造。?
設(shè)計(jì)出你可以合理要求的東西,好好開(kāi)發(fā)它。一旦完成,就拿給大家看,讓他們大吃一驚。然后說(shuō):“要是我們?cè)黾?..可能就會(huì)更好。”假裝那并不重要。坐回椅子上,等著他們開(kāi)始要你增加你本來(lái)就想要的功能。人們發(fā)現(xiàn),參與正在發(fā)生的成功要更容易。讓他們瞥見(jiàn)未來(lái),你就能讓他們聚集在你周圍。
6、記住大圖景?
Remember the Big Picture?
如果你抓一只青蛙放進(jìn)沸水里,它會(huì)一下子跳出來(lái)。但是,如果你把青蛙放進(jìn)冷水里,然后慢慢加熱,青蛙不會(huì)注意到溫度的緩慢變化,會(huì)呆在鍋里,直到被煮熟。?
不要像青蛙一樣。留心大圖景。要持續(xù)不斷地觀察周圍發(fā)生的事情,而不只是你自己在做的事情。
7、使質(zhì)量成為需求問(wèn)題?
Make Quality a Requirements Issue?
你所制作的系統(tǒng)的范圍和質(zhì)量應(yīng)該作為系統(tǒng)需求的一部分規(guī)定下來(lái)。讓你的用戶參與權(quán)衡,知道何時(shí)止步,提供足夠好的軟件。
8、定期為你的知識(shí)資產(chǎn)投資?
Invest Regularly in Your Knowledge Portfolio
- 讓學(xué)習(xí)成為習(xí)慣。
- 持續(xù)投入十分重要。一旦你熟悉了某種新語(yǔ)言或新技術(shù),繼續(xù)前進(jìn),學(xué)習(xí)另一種。
- 是否在某個(gè)項(xiàng)目中使用這些技術(shù),或者是否把它們放入你的簡(jiǎn)歷,這并不重要。學(xué)習(xí)的過(guò)程將擴(kuò)展你的思維,使你向著新的可能性和新的做事方式拓展。思維的“異花授粉”十分重要;設(shè)法把你學(xué)到的東西應(yīng)用到你當(dāng)前的項(xiàng)目中。即使你的項(xiàng)目沒(méi)有使用該技術(shù),你或許也能借鑒一些想法。例如,熟悉了面向?qū)ο?#xff0c;你就會(huì)用不同的方式編寫純C程序。
- 如果你自己找不到答案,就去找出能找到答案的人。不要把問(wèn)題擱在那里。
?
9、批判地分析你讀到的和聽(tīng)到的?
Critically Analyze What You Read and Hear?
不要被供應(yīng)商、媒體炒作、或教條左右。要依照你自己的看法和你的項(xiàng)目的情況去對(duì)信息進(jìn)行分析。10、你說(shuō)什么和你怎么說(shuō)同樣重要?
It's Both What You Say and the Way You Say It - 作為開(kāi)發(fā)者,我們必須在許多層面上進(jìn)行交流。我們的時(shí)間有很大部分都花在交流上,所以我們需要把它做好。
- 如果你不能有效地向他人傳達(dá)你的了不起的想法,這些想法就毫無(wú)用處。
- 知道你想要說(shuō)什么;了解你的聽(tīng)眾;選擇時(shí)機(jī);選擇風(fēng)格;讓文檔美觀;讓聽(tīng)眾參與;做傾聽(tīng)者;回復(fù)他人。
- 交流越有效,你就越有影響力。
?
11、DRY原則——不要重復(fù)你自己?
DRY - Don't Repeat Yourself?
系統(tǒng)中的每一項(xiàng)知識(shí)都必須具有單一、無(wú)歧義、權(quán)威的表示。與此不同的做法是在兩個(gè)或更多地方表達(dá)同一事物。如果你改變其中一處,你必須記得改變其它各處。這不是你能否記住的問(wèn)題,而是你何時(shí)忘記的問(wèn)題。12、讓復(fù)用變得容易?
Make it Easy to Reuse?
你要做的是營(yíng)造一種環(huán)境,在其中要找到并復(fù)用已有的東西,比自己編寫更容易。如果復(fù)用很容易,人們就會(huì)去復(fù)用。而如果不復(fù)用,你們就會(huì)有重復(fù)知識(shí)的風(fēng)險(xiǎn)。13、消除無(wú)關(guān)事物之間的影響?
Eliminate Effects Between Unrelated Things?
我們想要設(shè)計(jì)自足(self-contained)的組件:獨(dú)立,具有單一、良好定義的目的。如果組件是相互隔離的,你就知道你能夠改變其中一個(gè),而不用擔(dān)心其余組件。只要你不改變組件的外部接口,你就可以放心:你不會(huì)造成波及整個(gè)系統(tǒng)的問(wèn)題。?
你得到兩個(gè)主要好處:提高生產(chǎn)率與降低風(fēng)險(xiǎn)。14、不存在最終決策?
There Are No Final Decisions?
沒(méi)有什么永遠(yuǎn)不變——而如果你嚴(yán)重依賴某一事實(shí),你幾乎可以確定它將會(huì)變化。與我們開(kāi)發(fā)軟件的速度相比,需求、用以及硬件變得更快。通過(guò)DRY原則、解耦以及元數(shù)據(jù)的使用,我們不必做出許多關(guān)鍵的、不可逆轉(zhuǎn)的決策。有許多人會(huì)設(shè)法保持代碼的靈活性,而你還需要考慮維持架、部署及供應(yīng)商集成等領(lǐng)域的靈活性。15、用曳光彈找到目標(biāo)?
Use Tracer Bullets to Find the Target?
曳光彈能通過(guò)試驗(yàn)各種事物并檢查它們離目標(biāo)有多遠(yuǎn)來(lái)讓你追蹤目標(biāo)。?
曳光彈代碼含有任何一段產(chǎn)品代碼都擁有的完整的錯(cuò)誤檢查、結(jié)構(gòu)、文檔、以及自查。它只不過(guò)功能不全而已。但是,一旦你在系統(tǒng)的各組件之間實(shí)現(xiàn)了端到端(end-to-end)的連接,你就可以檢查你離目標(biāo)還有多遠(yuǎn),并在必要的情況下進(jìn)行調(diào)整。一旦你完全瞄準(zhǔn),增加功能將是一件容易的事情。16、為了學(xué)習(xí)而制作原型?
Prototype to Learn?
任何帶有風(fēng)險(xiǎn)的事物。以前沒(méi)有試過(guò)的事物,或是對(duì)于最終系統(tǒng)極其關(guān)鍵的事物。任何未被證明的、試驗(yàn)性的、或有疑問(wèn)的事物。任何讓你覺(jué)得不舒服的東西。都可以通過(guò)制作原型來(lái)研究。比如:架構(gòu);已有系統(tǒng)中的新功能;外部數(shù)據(jù)的結(jié)構(gòu)或內(nèi)容;第三方工具或組件;性能問(wèn)題;用戶界面設(shè)計(jì)等等。?
原型制作是一種學(xué)習(xí)經(jīng)驗(yàn),其價(jià)值并不在于所產(chǎn)生的代碼,而在于所學(xué)到的經(jīng)驗(yàn)教訓(xùn)。17、靠近問(wèn)題領(lǐng)域編程?
Program Close to The Problem domain?
計(jì)算機(jī)語(yǔ)言會(huì)影響你思考問(wèn)題的方式,以及你看待交流的方式。用你的用戶的語(yǔ)言進(jìn)行設(shè)計(jì)和編碼。18、估算,以避免發(fā)生意外?
Estimate to Avoid Surprises?
在著手之前先進(jìn)行估算。你將提前發(fā)現(xiàn)潛在的問(wèn)題。?
1)要選擇能反映你想要傳達(dá)的精確度的單位;?
2)基本的估算訣竅:去問(wèn)已經(jīng)做過(guò)這件事情的人;?
3)理解提問(wèn)內(nèi)容;?
4)根據(jù)對(duì)問(wèn)題的理解,建立粗略、就緒的思維模型骨架;?
5)把模型分解為組件,找出描述這些組件怎樣交互的數(shù)學(xué)規(guī)則,確定每個(gè)組件的參數(shù);?
6)給每個(gè)參數(shù)指定值,找出哪些參數(shù)對(duì)結(jié)果的影響最大,并致力于讓它們大致正確;?
7)進(jìn)行多次計(jì)算,改變關(guān)鍵參數(shù)的值,然后根據(jù)那些參數(shù)表達(dá)你的答案;?
8)在被要求進(jìn)行估算時(shí)說(shuō)的話:“我等會(huì)回答你”。19、通過(guò)代碼對(duì)進(jìn)度表進(jìn)行迭代?
Iterate the Schedule with the Code?
實(shí)行增量開(kāi)發(fā)。追蹤你的估算能力,提煉對(duì)迭代次數(shù)、以及在每次迭代中可以包含的內(nèi)容的猜想。提煉會(huì)變得一次比一次好,對(duì)進(jìn)度表的信心也將隨之增長(zhǎng)。你將給予管理部門你所能給予的最精確的進(jìn)度估算。20、用純文本保存知識(shí)?
Keep Knowledge in Plain Text - 保證不過(guò)時(shí);
- 杠桿作用:每一樣工具,都能夠在純文本上進(jìn)行操作;
- 更易于測(cè)試;
- 你需要確保所有各方能夠使用公共標(biāo)準(zhǔn)進(jìn)行通信。純文本就是那個(gè)標(biāo)準(zhǔn)。
?
21、利用命令shell的力量?
Use the Power of Command Shells?
GUI環(huán)境通常受限于它們的設(shè)計(jì)者想要提供的能力。當(dāng)你想要快速地組合一些命令,以完成一次查詢或某種其他的任務(wù)時(shí),命令行要更為適宜。多使用你的命令shell,你會(huì)驚訝它能使你的生產(chǎn)率得到怎樣的提高。22、用好一種編輯器?
Use a Single Editor Well?
選一種編輯器,徹底了解它,并將其用于所有的編輯任務(wù)。如果你用一種編輯器進(jìn)行所有的文本編輯活動(dòng),你就不必停下來(lái)思考怎樣完成文本操縱:必需的鍵擊將成為本能反應(yīng)。編輯器將成為你雙手的延伸;鍵會(huì)在滑過(guò)文本和思想時(shí)歌唱起來(lái)。這就是我們的目標(biāo)。23、總是使用源碼控制?
Always Use Source Code Control - 總是。即使你的團(tuán)隊(duì)只有你一個(gè)人,你的項(xiàng)目只有一周時(shí)間;確保每樣?xùn)|西都處在源碼控制之下。
- 源碼控制是你的工作的時(shí)間機(jī)器——你能夠回到過(guò)去。
- 把整個(gè)項(xiàng)目置于源碼控制系統(tǒng)的保護(hù)之下具有一項(xiàng)很大的、隱蔽的好處:你可以進(jìn)行自動(dòng)的和可重復(fù)的產(chǎn)品構(gòu)建。
?
24、要修正問(wèn)題,而不是發(fā)出指責(zé)?
Fix the Problem,Not the Blame?
要接受事實(shí):調(diào)試就是解決問(wèn)題,要據(jù)此發(fā)起進(jìn)攻。Bug是你的過(guò)錯(cuò)還是別人的過(guò)錯(cuò),并不是真的很有關(guān)系。它仍然是你的問(wèn)題。25、不要恐慌?
Don't Panic?
做一次深呼吸,思考什么可能是bug的原因。 - 要總是設(shè)法找出問(wèn)題的根源,而不只是問(wèn)題的特定表現(xiàn);
- 搜集所有的相關(guān)數(shù)據(jù);
- 開(kāi)始修正bug的最佳途徑是讓其可再現(xiàn);
- 使你的數(shù)據(jù)可視化;
- 跟蹤:觀察程序或數(shù)據(jù)結(jié)構(gòu)隨時(shí)間變化的狀態(tài);
- 找到問(wèn)題的原因的一種非常簡(jiǎn)單、卻又特別有用的技術(shù)是向別人解釋它。你只是一步步解釋代碼要做什么,常常就能讓問(wèn)題從屏幕上跳出來(lái),宣布自己的存在。
?
26、“Select”沒(méi)有問(wèn)題?
"Select" Isn't Broken?
Bug有可能存在于OS、編譯器、或是第三方產(chǎn)品中——但這不應(yīng)該是你的第一想法。有大得多的可能性的是,bug存在于正在開(kāi)發(fā)的應(yīng)用代碼中。與假定庫(kù)本身出了問(wèn)題相比,假定應(yīng)用代碼對(duì)庫(kù)的調(diào)用不正確通常更有好處。即使問(wèn)題確實(shí)應(yīng)歸于第三方,在提交bug報(bào)告之前,你也必須先消除你的代碼中的bug。27、不要假定,要證明?
Don't Assume it - Prove It?
不要因?yàn)槟恪爸馈彼芄ぷ鞫p易放過(guò)與bug有牽連的例程或代碼。證明它。在實(shí)際環(huán)境中——使用真正的數(shù)據(jù)和邊界條件——證明你的假定。28、學(xué)習(xí)一種文本操作語(yǔ)言?
Learn a Text Manipulation Language?
你用每天的很大一部分時(shí)間處理文本,為什么不讓計(jì)算機(jī)替你完成部分工作呢??
應(yīng)用示例: - 數(shù)據(jù)庫(kù)schema維護(hù);
- Java、C#屬性(Property)訪問(wèn);
- 測(cè)試數(shù)據(jù)生成。
?
29、編寫能編寫代碼的代碼?
Write Code That Writes Code?
代碼生成器能提高你的生產(chǎn)率,并有助于避免重復(fù)。30、你不可能寫出完美的軟件?
You Can't Write Perfect Software?
這刺痛了你?不應(yīng)該。把它視為生活的公理,接受它,擁抱它,慶祝它。因?yàn)橥昝赖能浖淮嬖凇T谟?jì)算機(jī)簡(jiǎn)短的歷史中,沒(méi)有一個(gè)人曾經(jīng)寫出過(guò)一個(gè)完美的軟件。你也不大可能成為第一個(gè)。除非你把這作為事實(shí)接受下來(lái),否則你最終會(huì)把時(shí)間和精力浪費(fèi)在追逐不可能實(shí)現(xiàn)的夢(mèng)想上。31、通過(guò)合約進(jìn)行設(shè)計(jì)?
Design with Contracts?
什么是正確的程序?不多不少,做它聲明要做的事情的程序。用文檔記載這樣的聲明,并進(jìn)行校驗(yàn),是按合約設(shè)計(jì)(簡(jiǎn)稱DBC)的核心所在。?
這里,強(qiáng)調(diào)的重點(diǎn)是在“懶惰”的代碼上:對(duì)在開(kāi)始之前接受的東西要嚴(yán)格,而允諾返回的東西要盡可能少。?
使用DBC的最大好處也許是它迫使需求與保證的問(wèn)題走到前臺(tái)來(lái)。在設(shè)計(jì)時(shí)簡(jiǎn)單地列舉輸入域的范圍是什么、邊界條件是什么、例程允諾交付什么——或者,更重要的,它不允諾交付什么——是向著編寫更好的軟件的一次飛躍。不對(duì)這些事項(xiàng)作出陳述,你就回到了靠巧合編程,那是許多項(xiàng)目開(kāi)始、結(jié)束、失敗的地方。32、早崩潰?
Crash Early?
死程序不說(shuō)謊。?
當(dāng)你的代碼發(fā)現(xiàn),某件被認(rèn)為不可能發(fā)生的事情已經(jīng)發(fā)生時(shí),你的程序就不再有存活能力。從此時(shí)開(kāi)始,它所做的任何事情都會(huì)變得可疑,所以要盡快終止它。死程序帶來(lái)的危害通常比有問(wèn)題的程序要小得多。33、如果它不可能發(fā)生,用斷言確保它不會(huì)發(fā)生?
If It Can't Happen,Use Assertions to Ensure That It Won't?
斷言驗(yàn)證你的各種假定。在一個(gè)不確定的世界里,用斷言保護(hù)你的代碼。?
不要用斷言代替真正的錯(cuò)誤處理。斷言檢查的是決不應(yīng)該發(fā)生的事情。34、將異常用于異常的問(wèn)題?
Use Exceptions for Exceptional Problems?
異常表示即使的、非局部的控制轉(zhuǎn)移——這是一種級(jí)聯(lián)的(cascading)goto。異常應(yīng)保留給意外事件。那些把異常用作其正常處理的一部分的程序,將遭受所有可讀性和可維護(hù)性問(wèn)題的折磨。這些程序破壞了封裝:通過(guò)異常處理,例程和它們的調(diào)用者被更緊密地耦合在一起。35、要有始有終?
Finish What You Start?
只要可能,分配某資源的例程或?qū)ο笠矐?yīng)該負(fù)責(zé)解除其分配。36、使模塊之間的耦合減至最少?
Minimize Coupling Between Modules - 編寫“羞怯”的代碼;
- 函數(shù)的得墨忒耳(Demeter)法則規(guī)定,某個(gè)對(duì)象的任何方法都應(yīng)該只調(diào)用屬于以下情形的方法:?
1)它自身;?
2)傳入該方法的任何參數(shù);?
3)它創(chuàng)建的任何對(duì)象;?
4)任何直接持有的組件對(duì)象。 - 物理解耦。
?
37、要配置,不要集成?
Configure,Don't Integrate?
細(xì)節(jié)會(huì)弄亂我們整潔的代碼——特別是如果它們經(jīng)常變化。把它們趕出代碼。當(dāng)我們?cè)谂c它作斗爭(zhēng)時(shí),我們可以讓我們的代碼變得高度可配置和“軟和”——也就是,容易適應(yīng)變化。?
要用元數(shù)據(jù)(metadata)描述應(yīng)用的配置選項(xiàng):調(diào)諧參數(shù)、用戶偏好(user preference)、安裝目錄,等等。38、將抽象放進(jìn)代碼,細(xì)節(jié)放進(jìn)元數(shù)據(jù)?
Put Abstractions in Code,Details in Metadata?
但我們不只是想把元數(shù)據(jù)用于簡(jiǎn)單的偏好。我們想要盡可能多地通過(guò)元數(shù)據(jù)配置和驅(qū)動(dòng)應(yīng)用。我們的目標(biāo)是以聲明方式思考(規(guī)定要做什么,而不是怎么做),并創(chuàng)建高度靈活和可適應(yīng)的應(yīng)用。我們通過(guò)采用一條一般準(zhǔn)則來(lái)做到這一點(diǎn):為一般情況編寫程序,把具體情況放在別處——在編譯的代碼庫(kù)之外。?
也許你在編寫一個(gè)具有可怕的工作流需求的系統(tǒng)。動(dòng)作會(huì)根據(jù)復(fù)雜的(和變化的)商業(yè)規(guī)則啟動(dòng)和停止。考慮在某種基于規(guī)則的系統(tǒng)(即專家系統(tǒng))中對(duì)它們進(jìn)行編碼,并嵌入到你的應(yīng)用中。這樣,你將通過(guò)編寫規(guī)則、而不是修改代碼來(lái)配置它。39、分析工作流,以改善并發(fā)性?
Analyze Workflow to Improve Concurrency?
時(shí)間是軟件架構(gòu)的一個(gè)常常被忽視的方面。時(shí)間有兩個(gè)方面對(duì)我們很重要:并發(fā)(事情在同一時(shí)間發(fā)生)和次序(事情在時(shí)間中的相對(duì)位置)。?
我們?cè)诰帉懗绦驎r(shí),通常并沒(méi)有把這兩個(gè)方面放在心上。當(dāng)人們最初坐下來(lái)開(kāi)始設(shè)計(jì)架構(gòu),或是編寫代碼時(shí),事情往往是線性的。那是大多數(shù)人的思考方式——總是先做這個(gè),然后再做那個(gè)。但這樣思考會(huì)帶來(lái)時(shí)間耦合:方法A必須總是在方法B之前調(diào)用;同時(shí)只能運(yùn)行一個(gè)報(bào)告;在接收到按鈕點(diǎn)擊之前,你必須等待屏幕重畫。“嘀”必須在“嗒”之前發(fā)生。?
這樣的方法不那么靈活,也不那么符合實(shí)際。?
我們需要容許并發(fā),并考慮解除任何時(shí)間或者次序上的依賴。40、用服務(wù)進(jìn)行設(shè)計(jì)?
Design Using Services?
實(shí)際上我們創(chuàng)建的并不是組件,而是服務(wù)——位于定義良好的、一致的接口之后的獨(dú)立、并發(fā)的對(duì)象。?
通過(guò)把你的系統(tǒng)架構(gòu)成多個(gè)獨(dú)立的服務(wù),你可以讓配置成為動(dòng)態(tài)的。41、總是為并發(fā)進(jìn)行設(shè)計(jì)?
Always Design for Concurrency?
首先,必須對(duì)任何全局或靜態(tài)變量加以保護(hù),使其免于并發(fā)訪問(wèn),現(xiàn)在也許是問(wèn)問(wèn)你自己、你最初為何需要全局變量的好時(shí)候。此外,不管調(diào)用的次序是什么,你都需要確保你給出的是一致的狀態(tài)信息。?
在被調(diào)用時(shí),對(duì)象必須總是處在有效的狀態(tài)中,而且它們可能會(huì)在最尷尬的時(shí)候被調(diào)用。你必須確保,在任何可能被調(diào)用的時(shí)刻,對(duì)象都處在有效的狀態(tài)中。這一問(wèn)題常常出現(xiàn)在構(gòu)造器與初始化例程分開(kāi)定義的類中(構(gòu)造器沒(méi)有使對(duì)象進(jìn)入已初始化狀態(tài))。?
一旦你設(shè)計(jì)了具有并發(fā)要素的架構(gòu),你可以靈活地處理應(yīng)用的部署方式:單機(jī)、客戶-服務(wù)器、或是n層。42、使視圖與模型分離?
Separate Views from Models?
也就是常說(shuō)的MVC模式(Model-View-Controller)。 - 模型。表示目標(biāo)對(duì)象的抽象數(shù)據(jù)模型。模型對(duì)任何視圖或控制器都沒(méi)有直接的了解。
- 視圖。解釋模型的方式。它訂閱模型中的變化和來(lái)自控制器的邏輯事件。
- 控制器。控制視圖、并向模型提供新數(shù)據(jù)的途徑。?
通過(guò)松解模型與視圖/控制器之間的耦合,你用低廉的代價(jià)為自己換來(lái)了許多靈活性。?
43、用黑板協(xié)調(diào)工作流?
Use Blackboards to Coordinate Workflow?
用黑板協(xié)調(diào)完全不同的事實(shí)和因素,同時(shí)又使各參與方保持獨(dú)立和隔離。?
現(xiàn)代的分布式類黑板(blackboard-like)系統(tǒng),比如JavaSpaces和T Spaces。44、不要靠巧合編程?
Don't Program by Coincidence - 總是意識(shí)到你在做什么。
- 不要盲目地編程。試圖構(gòu)建你不完全理解的應(yīng)用,或是使用你不熟悉的技術(shù),就是希望自己被巧合誤導(dǎo)。
- 按照計(jì)劃行事。
- 依靠可靠的事物。如果你無(wú)法說(shuō)出各種特定情形的區(qū)別,就假定是最壞的。
- 為你的假定建立文檔。“按合約編程”有助于澄清你頭腦中的假定,并且有助于把它們傳達(dá)給別人。
- 不要只是測(cè)試你的代碼,還要測(cè)試你的假定。
- 為你的工作劃分優(yōu)先級(jí)。
- 不要做歷史的奴隸。不要讓已有的代碼支配將來(lái)的代碼。?
所以下次有什么東西看起來(lái)能工作,而你卻不知道為什么,要確定它不是巧合。?
45、估算你的算法的階?
Estimate the Order of Your Algorithms?
在你編寫代碼之前,先大致估算事情需要多長(zhǎng)時(shí)間。46、測(cè)試你的估算?
Test Your Estimates?
對(duì)算法的數(shù)學(xué)分析并不會(huì)告訴你每一件事情。在你的代碼的目標(biāo)環(huán)境中測(cè)定它的速度。47、早重構(gòu),常重構(gòu)?
Refactor Early,Refactor Often?
在需要時(shí)對(duì)代碼進(jìn)行重寫、重做和重新架構(gòu)。要鏟除問(wèn)題的根源。不要容忍破窗戶。?
關(guān)于重構(gòu),詳見(jiàn)Martin Fowler的《重構(gòu)》一書(shū)。48、為測(cè)試而設(shè)計(jì)?
Design to Test?
在你還沒(méi)有編寫代碼時(shí)就開(kāi)始思考測(cè)試問(wèn)題。測(cè)試驅(qū)動(dòng)開(kāi)發(fā)?49、測(cè)試你的軟件,否則你的用戶就得測(cè)試?
Test Your Software,or Your Users Will?
測(cè)試是技術(shù),但更是文化。一點(diǎn)預(yù)先的準(zhǔn)備可以大大降低維護(hù)費(fèi)用、減少客戶服務(wù)電話。50、不要使用你不理解的向?qū)Тa?
Don't Use Wizard Code You Don't Understand?
向?qū)Ш芰瞬黄稹V恍枰c(diǎn)擊一個(gè)按鈕,回答一些簡(jiǎn)單的問(wèn)題,向?qū)Ь蜁?huì)自動(dòng)為你生成骨架代碼(skeleton code)。但如果你使用向?qū)?#xff0c;卻不理解它制作出的所有代碼,你就無(wú)法控制你自己的應(yīng)用。你沒(méi)有能力維護(hù)它,而且在調(diào)試時(shí)會(huì)遇到很大的困難。51、不要搜集需求——挖掘它們?
Don't Gather Requirements - Dig for Them?
需求很少存在于表面上。它們深深地埋藏在層層假定、誤解和政治手段的下面。52、與用戶一同工作,以像用戶一樣思考?
Work with a User to Think Like a User?
要了解系統(tǒng)實(shí)際上將如何被使用,這是最好的方法。開(kāi)采需求的過(guò)程也是開(kāi)始與用戶群建立和諧的關(guān)系、了解他們對(duì)你正在構(gòu)建的系統(tǒng)的期許和希望的時(shí)候。53、抽象比細(xì)節(jié)活得更長(zhǎng)久?
Abstractions Live Longer than Details?
“投資”于抽象,而不是實(shí)現(xiàn)。抽象能在來(lái)自不同的實(shí)現(xiàn)和新技術(shù)的變化的“攻擊”之下存活下去。54、使用項(xiàng)目詞匯表?
Use a Project Glossary?
如果用戶和開(kāi)發(fā)者用不同的名稱指稱同一事物,或是更糟,用同一名稱指稱不同事物,這樣的項(xiàng)目很難取得成功。55、不要在盒子外面思考——要找到盒子?
Don't Think Outside the Box - Find the Box?
在遇到不可能解決的問(wèn)題時(shí),問(wèn)問(wèn)自己以下問(wèn)題: - 有更容易的方法嗎?
- 你是在設(shè)法解決真正的問(wèn)題,還是被外圍的技術(shù)問(wèn)題轉(zhuǎn)移了注意力?
- 這件事情為什么是一個(gè)問(wèn)題?
- 是什么使它如此難以解決?
- 它必須以這種方式完成嗎?
- 它真的必須完成嗎??
很多時(shí)候,當(dāng)你設(shè)法回答這些問(wèn)題時(shí),你會(huì)有讓自己吃驚的發(fā)現(xiàn)。很多時(shí)候,對(duì)需求的重新詮釋能讓整個(gè)問(wèn)題全部消失。?
你所需要的只是真正的約束、令人誤解的約束、還有區(qū)分它們的智慧。?
56、傾聽(tīng)反復(fù)出現(xiàn)的疑慮——等你準(zhǔn)備好再開(kāi)始?
Listen to Nagging Doubts - Start When You're Ready?
你的一生都在積累經(jīng)驗(yàn)與智慧。當(dāng)你面對(duì)一件任務(wù)時(shí),如果你反復(fù)感覺(jué)到疑慮,或是體驗(yàn)到某種勉強(qiáng),要注意它。你可能無(wú)法準(zhǔn)確地指出問(wèn)題所在,但給它時(shí)間,你的疑慮很可能就會(huì)結(jié)晶成某種更堅(jiān)實(shí)的東西,某種你可以處理的東西。軟件開(kāi)發(fā)仍然不是科學(xué)。讓你的直覺(jué)為你的表演做出貢獻(xiàn)。57、對(duì)有些事情“做”勝于“描述”?
Some Things Are Better Done Than Described?
你應(yīng)該傾向于把需求搜集、設(shè)計(jì)、以及實(shí)現(xiàn)視為同一個(gè)過(guò)程——交付高質(zhì)量的系統(tǒng)——的不同方面。不要掉進(jìn)規(guī)范的螺旋,在某個(gè)時(shí)刻,你需要開(kāi)始編碼。58、不要做形式方法的奴隸?
Don't Be a Slave to Formal Methods?
如果你沒(méi)有把某項(xiàng)技術(shù)放進(jìn)你的開(kāi)發(fā)實(shí)踐和能力的語(yǔ)境中,不要盲目地采用它。59、昂貴的工具不一定能制作出更好的設(shè)計(jì)?
Expensive Tools Do Not Produce Better Designs?
小心供應(yīng)商的炒作、行業(yè)教條、以及價(jià)格標(biāo)簽的誘惑。在考察工具的產(chǎn)出時(shí),試著不要考慮它值多少錢。60、圍繞功能、而不是工作職務(wù)進(jìn)行組織?
Organize Around Functionality,Not Job Functions?
把你的人劃分成小團(tuán)隊(duì),分別負(fù)責(zé)最終系統(tǒng)的特定方面的功能。讓團(tuán)隊(duì)按照個(gè)人的能力,在內(nèi)部自行進(jìn)行組織。?
但是,只有在項(xiàng)目擁有負(fù)責(zé)的開(kāi)發(fā)者、以及強(qiáng)有力的項(xiàng)目管理時(shí),這種途徑才有效。創(chuàng)立一組自行其是的團(tuán)隊(duì)并放任自流,是一種災(zāi)難性的處方。?
要記住,團(tuán)隊(duì)是由個(gè)體組成的。讓每個(gè)成員都能以他們自己的方式閃亮。61、不要使用手工流程?
Don't Use Manual Procedures?
shell腳本或批處理文件會(huì)一次次地以同一順序執(zhí)行同樣的指令。我們可以自動(dòng)安排備份、夜間構(gòu)建、網(wǎng)站維護(hù)、以及其他任何可以無(wú)人照管地完成的事情。讓計(jì)算機(jī)去做重復(fù)、庸常的事情——它會(huì)做得比我們更好。我們有更重要、更困難的事情要做。62、早測(cè)試,常測(cè)試,自動(dòng)測(cè)試。?
Test Early.Test Often.Test Automatically.?
與呆在書(shū)架上的測(cè)試計(jì)劃相比,每次構(gòu)建時(shí)運(yùn)行的測(cè)試要有效得多。63、要等到通過(guò)全部測(cè)試,編碼才算完成?
Coding Ain't Done 'Til All the Tests Run?
就是這樣。64、通過(guò)“蓄意破壞”測(cè)試你的測(cè)試?
Use Saboteurs to Test Your Testing?
在單獨(dú)的軟件副本上故意引人bug,以檢驗(yàn)測(cè)試能夠抓住它們。65、測(cè)試狀態(tài)覆蓋,而不是代碼覆蓋?
Test State Coverage,Not Code Coverage?
確定并測(cè)試重要的程序狀態(tài)。只是測(cè)試代碼行是不夠的。即時(shí)具有良好的代碼覆蓋,你用于測(cè)試的數(shù)據(jù)仍然會(huì)有巨大的影響,而且,更為重要的是,你遍歷代碼的次序的影響可能是最大的。66、一個(gè)bug只抓一次?
Find Bugs Once?
一旦測(cè)試員找到一個(gè)bug,這應(yīng)該是測(cè)試員最后一次找到它。此后自動(dòng)測(cè)試應(yīng)該對(duì)其進(jìn)行檢查。67、把英語(yǔ)當(dāng)作又一種編程語(yǔ)言?
Treat English as Just Another Programming Language?
像你編寫代碼一樣編寫文檔:遵守DRY原則、使用元數(shù)據(jù)、MVC、自動(dòng)生成,等等。68、把文檔建在里面,不要拴在外面?
Build Documentation In,Don't Bolt It On?
與代碼分離的文檔不太可能被修正和更新。使用像JavaDoc和NDoc這樣的工具,我們可以根據(jù)源碼生成API級(jí)的文檔。?
文檔和代碼是同一底層模型的不同視圖,但視圖是唯一應(yīng)該不同的東西。69、溫和地超出用戶的期望?
Gently Exceed Your Users' Expectations?
要設(shè)法讓你的用戶驚訝。請(qǐng)注意,不是驚嚇?biāo)麄?#xff0c;而是要讓他們高興。要理解用戶的期望,然后給他們的東西要多那么一點(diǎn)。給系統(tǒng)增加某種面向用戶的特性所需的一點(diǎn)額外努力將一次又一次在商譽(yù)上帶來(lái)回報(bào)。70、在你的作品上簽名?
Sign Your Work?
我們想要看到對(duì)所有權(quán)的自豪。“這是我編寫的,我對(duì)自己的工作負(fù)責(zé)。”你的簽名應(yīng)該被視為質(zhì)量的保證。當(dāng)人們?cè)谝欢未a上看到你的名字時(shí),應(yīng)該期望它是可靠的、用心編寫的、測(cè)試過(guò)的和有文檔的,一個(gè)真正的專業(yè)作品,由真正的專業(yè)人員編寫。?
一個(gè)注重實(shí)效的程序員。
總結(jié)
- 上一篇: 『飞秋』Windows7新功能体验(1)
- 下一篇: 『飞秋』在ASP.NET服务器端过程中使