RSS   



  可打印版本 | 推薦給朋友 | 訂閱主題 | 收藏主題 | 純文字版  


 


 
主題: [轉貼]編程高手箴言-學習程式開發的方法   字型大小:||| 
ROACH
版主
等級: 30等級: 30等級: 30等級: 30等級: 30等級: 30等級: 30等級: 30
減肥中!請勿餵食

十週年紀念徽章(四級)  

 . 積分: 15118
 . 精華: 14
 . 文章: 11766
 . 收花: 140844 支
 . 送花: 6005 支
 . 比例: 0.04
 . 在線: 8869 小時
 . 瀏覽: 85616 頁
 . 註冊: 8003
 . 失蹤: 3
 . 鄉下地方
#1 : 2005-3-7 12:17 AM     全部回覆 引言回覆

《編程高手箴言》

作者:梁肇新
連接位址:
http://www.huachu.com.cn/2003/csdn.htm#7

大陸近期出版的一本書,偶然看到上面的網站上有放上第一章‘程式點滴’,
感覺裏邊有些東西還可以參考一下、就把它貼了上來
第一章下載位址:
http://www.huachu.com.cn/images/temp/434.rar


第1章 程 序 點 滴

好的開始是成功的一半,本書首先會試圖告訴你什麼是程式師?為什麼要做這樣的程式?正確的入門方法是什麼?
程式師只有在理解了以上內容的基礎上,才能進一步更快地提高自身技能,這時候再開始程式的設計。其實,對一個軟體的開發者來說,真正重要的不在於這行代碼怎麼寫,那些代碼應該怎麼寫,關鍵是思路的問題,而思路事實上是經驗的積累。經驗是使你從最初的封閉的思維方式,到最後形成開放式的思維的一個過程。將我十幾年程式生涯中獲得的一些經驗告訴讀者,使大家少走彎路也是我想寫這本書的主要目的。
1.1 程式≠軟體
現在很多人以為程式就是軟體,軟體就是程式。事實上,軟體和程式在20世紀80年代時,還可以說是等同的,或者說,在非PC領域裏它們可能還會是等同的,比如說某個嵌入式軟體領域,軟體和程式可能是等同的。但是,在PC這個領域內,現在的程式已不等於軟體了。這是什麼意思呢?
1. 軟體發展簡述
在20世紀80年代的時候,PC剛誕生,這時國內還沒有幾個人會寫程式。那麼,如果你寫個程式,別人就可以拿來用。這時候的程式就能產生價值,這個程式就直接等同於軟體。
但軟體行業發展到現在,這裏以中國的情況為例(美國在20世紀80年代,程式已經不等同於軟體了),程式也不等同於軟體了。因為現在會寫程式很容易,但是你的這個程式很難產生什麼樣的商業意義,也不能產生什麼價值,這就很難直接變成軟體。要使一個程式直接變成軟體,中間就面臨著很高的門檻問題。這個門檻問題來自於整個行業的形成。
現在,你寫了一個程式以後,要面臨商業化的過程。你要宣傳,你要讓用戶知道,你要建立經銷渠道,可能你還要花很多的時間去說服別人用你的東西。這是程式到軟體的一個過程。這門檻已比較高了。
我們在和國內的大經銷商的銷售渠道的人聊天時,他們的老闆說,這幾年做軟體的門檻挺高的,如果你沒有五、六百萬做軟體,那是“玩”不起來的。我說:“你們就使門檻很高了。”他說:“那肯定是的。如果你寫個“爛”程式,明天你倒閉了,你的東西還占了我的庫房,我還不知道找誰退去呢。我的庫房是要錢的呀!現在的軟體又是那麼多!”
所以,如果你沒有一定的資產的話,經銷商都不理你。實際情況也是這樣的,如果你的公司比較小,且沒什麼名氣,你的產品放到經銷商庫房,那麼他最多給你暫收,產品銷不動的話,一般兩周絕對會退貨。因為現在經銷商可選擇的餘地已很多了,所謂的軟體也已經很多了。而程式則更多,程式都想變成軟體,誰都說自己的是“金子”。但只有經受住用戶的檢驗,才能成為真正的“金子”。
這就是美國為什麼在20世紀90年代幾乎沒有什麼新的軟體公司產生的原因。只是原來80年代的大的軟體公司互相兼併,我吞你,你吃我。但是,寫程式的人很多,美國的程式變軟體的門檻可能比我們還高,所以很多人寫了程式就丟在網上,就形成了共用軟體。
2. 共用軟體
共用軟體是避開商業渠道的一種方法。它避開了商業的門檻,因為這個行業的門檻發展很高以後就輕易進不去了。我寫個程式丟在網上,你下載就可以用,這時候程式又等於軟體。共用軟體是這樣產生的,是因為沒有辦法中的辦法。如果說程式直接等於軟體的話,誰也不會輕易把程式丟到網上去。
開始做共用軟體的人並不認為做它能賺錢,只是後來用的人多了,有人付錢給他了。共用軟體使得程式和軟體的距離縮短了,但是它與商業軟體的距離會進一步拉大。商業軟體的功能和所要達到的目標就不是一個人能“玩”得起來的了。這時的軟體也已不是幾個人、一個小組就能做出來的了。這就是在美國新的軟體公司沒法產生的原因。比如Netscape網景是在1995~1996年產生的新軟體公司,但是,兩三年後它就不見了。
1.1.1 商業軟體門檻的形成
1. 商業軟體門檻的形成
商業軟體門檻的形成是整個行業發展的必然結果。任何一個行業初始階段時的門檻都非常低,但是,只要發展到一定的階段後,它的門檻就必然抬高。比如,現在國內生產小汽車很困難,但在20世紀50年代~60年代的時候,你裝4個輪子,再加上柴油機等就形成汽車。那時的萊特兄弟裝個螺旋槳,加兩個機翼,就能做飛機。整個行業還沒有形成的時候,絕對可以這樣做,但是,到整個行業形成時,你就做不了了。所有的行業都是這樣的。
為什麼網站一出來時那麼多人去擠著做?這也是因為一開始的時候,看起來門檻非常低,人人都可以做。只要有一個伺服器,架根網線,就能做網站。這個行業處於初始階段時,情況就是這樣的。但這個行業形成後,你就輕易地“玩”不了了。
國內的軟體發展也是如此。國內的軟體自從軟體經銷商形成以後,這個行業才真正地形成。有沒有一個渠道是判斷一個行業是否形成的很重要的環節。任何一個行業都會有一個經銷渠道,如果渠道形成了,那麼這個行業也就形成了。第一名的經銷商是1994年~1995年成立的,也就是說,中國軟體行業大概也就是在1995年形成的,至今才經歷8年時間的發展。
有一種浮躁的思想認為,中國軟體產業應該很快就能趕上美國。美國軟體行業是上世紀80年代形成的,到現在已經發展了20多年了。中國軟體行業才8年,8年才是一個懵懂的小孩,20多歲是一個強壯的青年,那麼他們的力量是不對等的。但也要看到,當8歲變成15歲的時候,它真正的能量才會反映出來。
2. 軟體門檻對程式師的影響
現在中國軟體行業正在形成。所以,現在做一個程式師一定要有耐心,因為現在已經不等於以前了。你一定要把所有的問題搞清楚,然後再去做程式。
對於程式師來說,最好的工作環境是在現有的或者初始要成立的公司裏面,這是最容易成功的。個人單槍匹馬闖天下已經很困難了。即使現在偶爾做兩個共用軟體放在網上能成名,但是也已經比較困難了。因為現在做軟體的人已經很多了。這也說明軟體已經不等於程式了,程式也不等於軟體。
程式要變成軟體,這中間是一個商業化的過程。沒有門檻以前,它沒有這個商業過程,現在有這個行業了,它中間就有商業化的過程。這個商業的過程就不是一個人能“玩”的。
如果你開始做某一類軟體的時候,別人已經做成了,這時你再決定花力氣去做,那麼你就要花雙倍的力氣去趕上別人。
現在的商業軟體往往是由很多模組組成的,模組是整個系統的一部分。個人要完整地寫一個商業系統幾乎是不可能的。軟體進入Windows平臺後,它已經很複雜了,不像在DOS的時候,你寫兩行程式就能賣,做個ZIP也能賣。事實上,美國的商業編譯器也不是一個人能“玩”的。現在你可能覺得它是很簡單的,甚至Linux還帶了一個GCC,且根源程式還在。你可以把它改一改,做個VC試一試,看它會有人用嗎?它能變成軟體嗎?即使你再做個介面,它也還是一個GCC,絕對不會成為Visual C++那樣能商業化的軟體。
可見,國外軟體行業的門檻要比中國的高很多了。我覺得我們中國即使再去做這樣的東西,也沒有多大的意義了。這個門檻你是追不過來的。不僅要花雙倍的力氣,而且在這麼短的時間內,你還要完成別人已經完成過的工作,包括別人所做的測試工作。只有這樣,才能做到你的軟體與別人有競爭力,能與它做比較。
1.1.2 認清自己的發展
如果連以上認識都不清楚,很可能就以為去書店買一本MFC高手速成之類的書,編兩個程式就能成為軟體高手。就好像這些書是“黃金”,我學兩下,學會了VC、MFC,就能做一個軟體拿出去賣了。這種想法也不是不行,最後一定能行,但要有耐心,還要有機遇。機遇是從耐心中產生的,越有耐心,就越有機遇。你得非常努力,要花很多的精力,可能還要走很多的彎路。
如果你是從MFC入手的,或是從VB入手的,則如要做出一個真正的能應用個人領域的通用軟體,就會走非常多的彎路。直接的捷徑絕對不是走這兩條路。這兩條路看起來很快,而且在很多公司裏面確實需要這樣的東西,比如說我這家公司就是為另一個家公司做系統集成的,那我就需要這樣的東西,我不管你具體怎麼實現,我只需要達到這個目標就行了。
任何軟體的實現都會有n種方法,即使你是用最差的那種方法實現的,也沒有問題,最後它還是能運行。即使有問題,再改一改就是。但是,做通用軟體就不行了,通用是一對多,你做出來的軟體以後要面向全國,如果將來自由貿易通到香港也好,通到國外也好,整個產品能銷到全世界的話,這時候,通用軟體所有做的工作就不是這麼簡單了。所以說,正確的入門方法就很關鍵。
如果你僅僅只是想混口飯吃,找個工作,可能教你成為MFC的高手之類的書對你就足夠了。但是,如果你想做一個很好的軟體,不僅能滿足你謀一碗飯吃,還能使你揚名,最後你的軟體還能成為很多人用,甚至你還想把它作為一個事業去經營,那麼這第一步就非常關鍵。這時就絕對不能找一本MFC或找一本VB的書學兩下就行,而是要從最底層開始做起,從最基本做起。
1.2 高手是怎樣練成的
1.2.1 高手成長的六個階段
程式師怎樣才能達到編程的最高境界?最高境界絕對不是你去編兩行代碼,或者是幾分鐘能寫幾行代碼,或者是用什麼所謂的視覺化工具產生最少的代碼這些工作,這都不是真正的高手境界。即使是這樣的高手,那也都是無知者的自封。
我認為,一個程式師的成長可分為如下六個階段。
贯 第一階段
此階段主要是能熟練地使用某種語言。這就相當於練武中的套路和架式這些表面的東西。
贯 第二階段
此階段能精通基於某種平臺的介面(例如我們現在常用的Win 32的API函數)以及所對應語言的自身的庫函數。到達這個階段後,也就相當於可以進行真實散打對練了,可以真正地在實踐中做些應用。
贯 第三階段
此階段能深入地瞭解某個平臺系統的底層,已經具有了初級的內功的能力,也就是“手中有劍,心中無劍”。
贯 第四階級
此階段能直接在平臺上進行比較深層次的開發。基本上,能達到這個層次就可以說是進入了高層次。這時進入了高級內功的修煉。比如能進行VxD或作業系統的內核的修改。
這時已經不再有語言的束縛,語言只是一種工具,即使要用自己不會的語言進行開發,也只是簡單地熟悉一下,就手到擒來,完全不像是第一階段的時候學習語言的那種情況。一般來說,從第三階段過渡到第四階段是比較困難的。為什麼會難呢?這就是因為很多人的思想變不過來。
贯 第五階級
此階段就已經不再局限於簡單的技術上的問題了,而是能從全局上把握和設計一個比較大的系統體系結構,從內核到外層介面。可以說是“手中無劍,心中有劍”。到了這個階段以後,能對市面上的任何軟體進行剖析,並能按自己的要求進行設計,就算是MS Word這樣的大型軟體,只要有充足的時間,也一定會設計出來。
贯 第六階級
此階段也是最高的境界,達到“無招勝有招”。這時候,任何問題就純粹變成了一個思路的問題,不是用什麼代碼就能表示的。也就是“手中無劍,心中也無劍”。
此時,對於練功的人來說,他已不用再去學什麼少林拳,只是在旁看一下少林拳的對戰,就能把此拳拿來就用。這就是真正的大師級的人物。這時,Win 32或Linux在你眼裏是沒有什麼差別的。
每一個階段再向上發展時都要按一定的方法。第一、第二個階段通過自學就可以完成,只要多用心去研究,耐心地去學習。
要想從第二個階段過渡到第三個階段,就要有一個好的學習環境。例如有一個高手帶領或公司裏有一個好的練手環境。經過二、三年的積累就能達到第三個階段。但是,有些人到達第三個階段後,常常就很難有境界上的突破了。他們這時會產生一種觀念,認為軟體無非如此,認為自己已無所不能。其實,這時如果遇到大的或難些的軟體,他們往往還是無從下手。
現在我們國家大部分程式師都是在第二、三級之間。他們大多都是通過自學成才的,不過這樣的程式師一般在軟體公司也能獨當一面,完成一些軟體的模組。
但是,也還有一大堆處在第一階段的程式師,他們一般就能玩玩VB,做程式時,去找一堆控制項集成一個軟體。
現在一種流行的說法是,中國軟體人才現在是一個橄欖型的人才結構,有大量的中等水平的程式師,而初級和高級程式師比較少。而我認為,現在中國絕大多數都是初級的程式師,中級程式師很少,高級的就更少了。所以,現在的人才結構是“方塔”形,這是一種斷層的不良結構。而真正成熟的軟體人才結構應該是平滑的三角形結構。這樣,初級、中級、高級程式師才能充分地各施所長。三種人才結構對比如圖1.1所示。

圖1.1 三種人才結構對比
1.2.2 初級程式師和高級程式師的區別
一般對於一個問題,初級程式師和高級程式師考慮這個問題的方法絕對是不同的。比如,在初級程式師階段時,他會覺得VB也能做出應用來,且看起來也不錯。
但到了中級程式師時,他可能就不會選擇VB了,可能會用MFC,這時,也能做出效果不錯的程式。
到高級程式師時,他絕對不是首先選擇以上工具,VB也好,VC也好,這些都不是他考慮的問題。這時考慮的絕對是什麼才是具有最快效率、最穩定性能的解決問題的方法。
軟體和別的產品不同。比如,在軟體中要達到某個目標,有n種方法,但是在n種方法中,只有一種方法或兩種方法是最好的,其他的都很次。所以,要做一個好的系統,是很需要耐心的。如果沒有耐心,就不會有細活,有細活的東西才是好東西。我覺得做軟體是這樣,做任何事情也是這樣的,一定要投入。

程式師到達最高境界的時候,想的就是“我就是程式,程式就是我”。這時候我要做一個軟體,不會有自己主觀的思路,而是以機器的思路來考慮問題,也就是說,就是以程式的思考方式來思考程式,而不是以我去設計程式的方式去思考程式。這一點如果不到比較高的層次是不能明白的。
你設計程式不就是你思考問題,然後按自己的思路去做程式嗎?
其實不是的。在我設計這個程式的時候,相當於我“鑽”入這個程式裏面去了。這時候沒有我自己的任何思維,我的所有思維都是這個程式,它這步該怎麼走,下步該怎麼走,它可能會出現什麼情況。我動這個部分的時候,別的部分是否要幹擾,也許會動一發而牽全身,它們之間是怎麼相互影響的?
也只有到達這個境界,你的程式才能真正地寫好,絕對不是做個什麼視覺化。視覺化本身就是“我去設計這個程式”,而真正的程式高手是“我就是程式”,這兩種方法絕對是不同的。比如,我要用VB去設計一個程式,和我本身就是一個程式的思維方式,是不一樣的。別人也許覺得作業系統很深奧,很複雜,其實,如果你到達高手狀態,你就是作業系統,你就能做任何程式。
對待軟體要有一個全面的分析方法,光說理論是沒有用的。如果你沒有經過第一、第二、第三、第四這四個階段,則永遠到達不了高境界。因為空中樓閣的理論沒有用,而這些必須是一步一步地去做出來。
一個高級程式師應該具備開放性思維,從裏到外的所有的知識都能瞭解。然後,看到世界最新技術就能馬上掌握,馬上瞭解。實際上,技術到達最高的境界後,是沒有分別的。任何東西都是相通的,只要你到達這個境界以後,什麼問題一看就能明白,一看就能抓住最核心的問題,最根本的根本,而不會被其他的枝葉或表像所迷惑,做到這一步後才算比較成功。
從程式師本身來說,如果它到達這一步以後,他就已經形成了開闊的思維。他有這種開放性思維的話,他就能做戰略決策,這對他將來做任何事情都有好處。事實上,會做程式後,就會有一種分析問題的方法,學會怎麼樣把問題的表像剖開,看到它的本質。這時你碰到任何具體的問題,只要給點時間,都能輕而易舉地解決。實際上,對開發電腦軟體來說,沒有什麼做不了的軟體,所有的軟體都能做,只是看你有沒有時間,有沒有耐心,有沒有資金做支撐。
這幾年,尤其是這兩三年,估計到2005年前,中國軟體這個行業裏面大的軟體公司就能形成。現在就已經在形成,例如用友,它上市後,地位就更加穩固了。其他大的軟體企業會在這幾年內迅速長大。這時候,包括流通渠道、經銷商的渠道也會迅速長大。也就是說,到2005年以後,中國軟體這個行業的門檻比現在還要高很多,與美國不會有太大的差別。此時,中國軟體才真正體現出它的威力來。如果你是這些威力中的一員,就已經很厲害了。
別人可能知道比爾•蓋茨是個談判的高手,是賣東西的高手,其實,比爾•蓋茨從根本上來說是個程式高手,這是他根本中的根本。他對所有的技術都非常敏感,一眼就看到本質,而且他本身也能做程式,時常在看程式。現在他不做董事長,而做首席設計師,這時他就更加接近程式的本質。因為他本身就有很開闊的思維,又深入到技術的本身,所以他就知道技術的方向。這對於一個公司,對他這樣的人來說,是非常重要的。
如果他判斷錯誤一步,那公司以後再回頭就很難了。電腦的競爭是非常激烈的,不能走錯半步。很多公司以前看上去很火,後來就
銷聲匿跡了,就是因為它走錯一步,然後就不行了。為什麼它會走錯?因為他不瞭解技術的本質在哪里,技術的發展方向在哪里。
比爾•蓋茨因為父母是學法律的,所以他本身就很能“侃”,很有說服力,而他又是做技術的,就非常清楚技術的方向在哪里,所以他才能把方向把握得很準確,公司越來越大。而別的公司只火一陣子,他卻火了還會再火。就算微軟再龐大,你如果不把握好軟體技術的最前沿,一樣也會玩完。就像Intel時刻把握著CPU的最新技術,才能保證自己是行業老大。技術決定它的將來。

所以,程式師要能達到這樣的目標,就要有非常強的耐心和非常好的機遇才有可能。事實上,現在的機會挺好的,2005年以前機會都非常大,以後機會會比較小。但是,如果有耐心的話,你還是會有機會的,機會都是出在耐心裏。我記得有句話說“雄心的一半是耐心”,我認為雄心的三分之二都是耐心。如果你越有野心,你就越要有耐心,你的野心才有可能實現。如果你有野心而沒有耐心,那都是胡思亂想,別人一眼就能看穿。最後在競爭中,對手一眼就看到你的意圖,那你還有什麼可競爭的?
1.2.3 程式師是吃青春飯的嗎
很多人都認為程式師是三十歲以前的職業,到了三十歲以後,就不應再做程式師了。現在的很多程式師也有這種想法,我覺得這種想法很不對。
在20世紀80年代末到90年代初,那時軟體還沒有形成行業,程式師不能以此作為謀生的手段時,你必須轉行,因為你年輕的時候不用考慮吃飯的問題,天天“玩”都可以,但是以後就不可能了。
據我瞭解,微軟裏面的那些高手,幾乎都是四五十歲的,而且都是做底層的。他們是上世紀70年代就開始“玩”程式的,所以對於整個電腦,他們是太清楚了。現在有些人主觀臆斷地希望微軟第二天倒閉就好了,但那可能性太小了。因為那些程式師是從CPU是4004的時候開始,玩到現在奔騰IV,沒有哪一代東西他們沒有經歷過。
你知道他們現在正在玩什麼嗎?現在正在玩64位的CPU。你說你普通的程式師,有這個耐心嗎?沒有這個耐心,你絕對做不了,你也絕對做不了高手。他為什麼能做?因為他不僅是玩過來的,而且他還非常有耐心,每一步技術他都跟得上,所以對他來說,沒有任何的難度和壓力。
因為電腦技術沒有任何時候是突變的。它的今年和去年相差不會很大,但是回過頭來看三年以前的情況,和現在的距離就很大。所以說,如果你每年都跟著技術進步的話,你的壓力就很小,因為你時刻都能掌握最新的技術。但是,如果你落下來,別說十年,就是三年,你就趕不上了。
如果你一旦趕不上,就會覺得非常吃力;如果你趕不上,你就會迷失方向;如果你迷失了方向,你就覺得電腦沒有味道,越做越沒勁。當你還只是有個思路的時候,別人的產品都做出來了,因為你的水平跟別人相差太遠,人家早就想到的問題,你現在才開始認識。水平越高,他就看得越遠,那麼他的思維就越開闊;水平越低,想的問題就越窄。
64位CPU是這個十年和下個十年最重要的技術之一,誰抓住這個機會,誰就能抓住未來賺錢的商機。CPU是英代爾設計的,對這一點他肯定清楚。舉例來說,如果從64位的角度來看現在的32位,就像從現在的角度去看DOS。你說DOS很複雜嗎?當你在DOS年代的時候,你會覺得DOS很複雜。你說現在的Windows不夠複雜嗎?Windows太複雜了,但是你到了64位的時候再去看Windows,就如同現在看DOS一樣。
整個64位元系統的平臺和思維方式、思路都比現在更開闊,打個比方說,現在的Windows裏面能開n個DOS視窗,每個DOS窗都能運行一個程式。到達64位元的時候,作業系統事實上能做到開n個X86,開n個Windows 98,然後再開n個Windows 95都沒有問題,系統能做到這一步,甚至你的系統內開n個Windows NT都沒有關係。這就是64位和32位的差別。所以,微軟的那些“老頭”,四、五十歲的那幾個做核心的人,現在正在玩這些東西。你說微軟的技術它能不先進嗎?是Linux那幾個玩家能搞定的嗎?
微軟的技術非常雄厚,世界電腦的最新技術絕對集中在這幾個人手裏。而且這幾個人的思維模式非常開闊,誰都沒有意識到的東西他早就開始做了。現在64位的CPU都出來一二年了,你說有什麼人去做這些應用嗎?沒有,有的就是那幾個UNIX廠商做好後給自己用的。

所以,追求技術的最高境界的時候,實際上是沒有年齡限制的。對我來說,現在都三十三了,我從來沒有想過退出這行,我覺得我就能玩下去,一直玩到退休都沒有問題。我要時刻保持技術的最前端,這樣的話對我來說是不困難的,沒有任何累的感覺。
很多人說做程式不是人幹的事情,是非人的待遇。這樣,他們一旦成立一個公司,做出一點成績,在輝煌的時候馬上就考慮退出。因為他們太苦了,每天晚上熬夜,每天晚上燒了兩包煙還不夠,屋子裏面簡直就缺氧了,好像還沒有解決問題。
白天睡覺,晚上幹活,那當然累死了,這是自己折騰自己。所以,做程式師一定要有一種正常的心態,就是說,你做程式的時候,不要把自己的生活搞得顛三倒四的。如果非得搞得晚上燒好多煙才行,這樣你肯定折騰不到三十歲,三十歲以後身體就差了。
事實上,我基本上就沒有因為做程式而熬夜的。我只經歷過三次熬夜,一次是在學校的時候,1986年剛接觸電腦時,一天晚上跟一個同桌在電腦室內玩遊戲,研究了半天,搞著搞著就到了天亮,這是第一次。然後在畢業之前,在286上做一個程式。還有一次就是超級解霸上市前,那時公司已吹得很大了,那天晚上沒法睡覺。
一般來說,我也是十二點鐘睡覺,第二天七點就起了。所以說,只有具有正常的生活、正常的節奏,才有正常的心態來做程式師,這樣,你的思路才是正常的,只有正常的東西才能長久。搞疲勞戰或者是黑白顛倒,時間長久後就玩不轉了,玩著玩著就不想玩了。
只要你不想玩,不瞭解新技術,你就會落後,一旦落後,你再想追,就很難了。
1.3 正確的入門方法
在這一節中,主要講從我的經驗來看,一般程式師需要注意的地方。教你怎樣去具體學習不是我的責任,你可以去任何一個書店去找一本書回來自己看就可以了。這裏只是對這些書做一些補充以及一些平常從來沒注意的內容。
入門最基本的方法就是從C語言入手。如果以前學過BASIC語言的話,那麼從C語言入手是非常容易的。我就經歷了一個過程,根本不覺得這中間有太大的難度。其實,C語言本身和BASIC沒有什麼兩樣。BASIC每個所謂的命令在C語言裏面都可以做成一個函數來實現,那麼你就能用那個命令組合成整個程式。從這個角度來看,BASIC和C語言沒有本質的差別。C語言就是入門的正確方法,沒有其他。
現在的C語言本身就包含了嵌入彙編,使學習組合語言的時候更加方便。你可以忽略掉純彙編裏面的很多操作。也許有人覺得這個方法太慢了。但要知道,工欲善其事,必先利其器,要想成功,沒有一個艱苦的過程是不可能的,所以一開始的時候就要有耐心。如果你準備花5年的時間成為高手,那我敢說,你根本不用等到5年,你只要有這個耐心就足夠了,你可能2年~3年內就能達到目標。但如果你想在一年時間內就成為高手,即使5年後,你還是成不了高手。
我們公司1998年招的開發人員都是應屆大學畢業生。很明顯,有人好像什麼都會,又會CorelDraw,又會Photoshop,又會Flash,又會C++,甚至VB也會。可是這樣的人到現在還是全都會,但是什麼事情也做不好,做的東西“臭”死了。但其中有一個人就不同,他以前甚至連Windows的程式都沒有做過,只會在DOS下做幾個小程式。但當我們把超級解霸的程式給他看,讓他去研究的時候,他只用一周的時間,就迅速掌握。他那個月進步非常快,幾乎就是一生中進步最快的階段,這就是一個質的飛躍。
從基本入手以後,當你的積累到達一個階段以後,就會有一個質的飛躍的階段。事實上,我也有這麼一個階段,這個階段也是我離開大學以後,真正去公司做事的時候。當我真正擁有一台電腦後,我把所有以前積累的問題在一個月內做了探討以後,感覺自己的水平迅速提高。

入門和積累是很重要的。事實上,到達高手的境界以後,不管什麼語言不語言的,其實都根本不用去學,只要拿過來看兩天,就全部精通。如果你沒有入門,即使去書店找n本書,天天背它,你也不會成為高手。
所有的語言只是很花哨的表面東西。高手馬上就能透過它的表像而看到它的本質。這樣才是真正的高手。他不需要再去學什麼Java,或者其他什麼語言。當他真正要寫個Java程式的時候,只要把Java程式拿過來看一看,瞄一瞄書,就全都清楚了。如果這時他學VB就更容易了,我想他不用一天的時間,就能學會。到達高手的境界以後,所有的事物都是觸類旁通的。
當你成為C語言的高手,那麼就你很容易進入到作業系統的平臺裏面去;當你進入到作業系統的平臺裏去實際做程式時,就會懂得進行調試;當你懂得調試的時候,你就會發現能輕而易舉地瞭解整個平臺的架構。這時候,電腦基本上一切都在你的掌握之中了,沒有什麼東西能逃得出你的手掌心。
上面只是針對程式的角度說明,另外一點也很重要,即好的程式師必須具備開放性思維,也就是思考問題的方法。程式師,尤其現在很多的程式師,都被誤導從MFC入手,這就很容易形成一種封閉式的思維模式。這也是微軟希望很多人只能學點表面的東西,不致成為高手,所以他大力推薦MFC之類的工具,但也真有很多人願意去上他的當,最後真正迷失方向。說他做不了程式吧,他也能做程式,但是如果那個程式複雜一點,出現問題時,問題出在哪里就搞不清楚了,反正是不清楚。如果你真正有一種開放性的思維,在你能夠成為高級程式師的時候,對MFC這些是不屑一顧的,MFC、VB根本不會在考慮的範圍之內。
事實上很多人,包括外面很多公司裏面工資挺高的人,可能一個月能拿五、六萬的這些人,他們的思維也不一定能達到很高的境界。但是,他確實做了很多的事情,已經有很好的積累了。但要上升到更高的境界上,就要有正確的思維方法。這就是為什麼比爾•蓋茨說,他招人的時候寧願招一個學物理,而不是學編程的。學物理的人會有非常非常廣的思維,他考慮的小到粒子,大到宇宙,思維空間非常廣闊,這樣,他思考問題的時候,就會很有深度。
有人研究物理研究得比較深的時候,他能針對某個問題一直深入進去。很多寫程式的人只會注意到這行代碼或那行代碼,則比較起來則顯得膚淺。所以,編程的時候也要深入進去,把你的愛好、你的所有思維都放進去,努力做到物我合一的境界。
1.3.1 規範的格式是入門的基礎
以前所有的C語言的書中,不太重視格式的問題,寫的程式像一堆堆的垃圾一樣。這也導致了現在的很多程式師的程式中有很多是廢碼、垃圾代碼,這和那些入門的書非常有關係。因為這些書從不強調代碼規範,而真正的商業程式絕對是規範的。你寫的程式和他寫的程式應該格式大致相同,否則誰也看不懂。如果寫出來的代碼大家都看不懂,那絕對是垃圾。如果把那些垃圾“翻”半天,勉強才能把裏面“金子”找出來,那這樣的程式不如不要,還不如重新寫過,這樣,思路還會更清楚一點。這是入門首先要注意的事情,即規範的格式是入門的基礎。
1. 成對編碼
正確的程式設計思路是成對編碼,先寫上面的大括弧,然後馬上寫下面的大括弧。這樣一個函數體就已經形成了。它沒有任何問題。然後,比如你要寫個for迴圈,這時候先申明一個變數I,再寫這個for迴圈。寫上面的大括弧,馬上寫下面的大括弧,然後再在中間插一二行代碼。插這段代碼後,如果你又要用到新變數,則再在頭上添加新的變數,然後再讓它進行工作。這就是一種成對編碼。
這樣,當你用到一個記憶體的時候,寫一個分配函數分配一塊記憶體,馬上就接著寫釋放這塊記憶體的代碼。然後你再在中間插上你要用這個記憶體做什麼。這是正確的快速的編程方法。否則,你去查或調試代碼都無從下手。針對這個程式來說,如果用成對編碼,則它任何時候都是可以調試的,不需要你整個程式都寫完後才能進行調試。
它是任何時候都可以編譯調試的,甚至你寫了兩個大括弧,中間什麼也沒有,它是空的時,你都可以進行調試。你寫了第一個for迴圈,它也可以進行調試,當你又寫了一個分配記憶體、釋放記憶體以後,它還可以進行調試。它可以編譯運行,裏面可以放中斷點,這就是成對編碼。
成對編碼就涉及到代碼規範的問題。為什麼我說上面一個大括弧,下面一個大括弧,而不說成是前面一個大括弧,後面一個大括弧呢?如果是一般C語言的書,則它絕對說是後面加個大括弧,回過頭前面加個大括弧。事實上,這就是垃圾程式的寫法。正確的思路是寫完行給它回車,給它大括弧獨立的一行,下面大括弧也是獨立的一行,而且這兩個大括弧跟那個for單詞中間錯開一個TAB。
集成環境的TAB首先要設成8,因為TAB的基本定義就是8,而現在的VC把它設成了4,這樣使得你編出的程式放到一個標準的環境裏看的時候就是亂的。
代碼一定不能亂,一定要格式非常清楚,這點使你寫的程式我能讀,我寫的程式你也能讀,不需要再去習慣彼此的不同寫法。
而且結合成對編碼思維,這時候你去讀一個程式的時候,你會發現,你讀程式的方法變了。以前讀程式的時候,你可以先去讀它的變數是什麼,然後再讀第一行、第二行,讀到最後一個大括弧,這是一種讀程式的方法。現在就不一樣了,現在讀程式的時候就養成了一種習慣,就是分塊閱讀程式,很明顯兩個大括弧之間就是一塊代碼。
那麼寫出一個程式後,你要讀這個程式是幹什麼的,只要看這個大括弧和那個大括弧之間的部分就可以了,不需要再去讀其他的代碼是幹什麼的。比如,你從Linux中或網上下載了一個“爛”程式後,該怎麼去閱讀它?最好的方法是先把程式所有的格式都整理好,先別去讀它。把所有的格式按照這種規範化的方法,把它的括弧全部整理好。這時候你再讀那個程式,只要半分鐘就讀懂了,但是你可能要整理一個小時。但如果不這樣做,你可能讀兩個小時都讀不清楚該程式。
這點絕對不會有人告訴你,現在沒有人去講解這方面的技巧。這也是我寫了那麼多的程式,才總結出來的。一開始的時候,我也像那些教科書所教導那樣寫,後面放個大括弧,前面放個大括弧,甚至括弧連括弧,一連四個括弧,每個括弧對哪個最後都找不清楚。編譯告訴你好像少了一個括弧,於是找呀,找呀,上面找,下面找,而這個程式又很大,只有一個函數,上面在上屏,下面在下屏,最後翻來翻去也翻不出。
所以我就想,大括弧之間要互相對應,即使不在一個螢幕內,也能很容易地看到它,因為只要遊標落在這個大括弧裏面,往上去找,即能找到它頭上的那個與此對正的,而且這些代碼是在一起的。這一層代碼和下一層代碼是互相隔開的,我只要讀這層代碼,下面那一層代碼就不需要了。
比如,它有n個for迴圈的時候,我只想看某一個for迴圈,這時我只要對正大括弧,它的遊標往上走,一下就能找到了。如果按照教科書那樣寫的話,你要讀呀,讀呀,要把所有的代碼,把所有的for
迴圈都讀一遍,才可能找到你要的東西。這就是成對編碼和規範化的方法(詳細敍述請參考代碼規範一章)。

代碼中如果不包括正確的思路,那該代碼就沒有什麼用。如果是一個代碼愛好者去收集代碼,而現在網路上代碼成群,Linux本身就帶了一大堆的程式,那些程式對你真的有用嗎?我看不見得。而且那些程式還在不斷地升級,那程式還會有新版,如果你把它拿來看一下,對你來說其實沒什麼價值。
那怎麼樣使得它對你有用?就必須用上面所說的方法,經過這麼處理以後,你就能真正取到它其中的設計思路,這樣才能變廢為寶。如果是MFC之類的東西,那你就不用找了,因為即使找,也找不出有價值的東西,全部是VC自動給你生成的一堆堆的垃圾框架,相對於網上Linux程式來說,它可能更“臭”一些。
在軟體沒有形成行業,程式等同於軟體的時候,那時候程式很容易體現出價值來。只要得到代碼,就相當於得到這個軟體。但現在就不同了。現在的程式都不是幾行,你寫出的程式,如果又沒有注釋,格式又很亂,你拿過來給我,我還得花很長的時間才能讀得清楚,那這樣的程式的代碼有價值嗎?
我經常聽到一些程式師在外面兜銷代碼,很多是學校的學生,尤其那些素質比較差的研究生,和老師做了一個項目後,他拿出來到外面到處去賣,但是他最後可能賣出去嗎?最後可能還是沒賣出去,因為那個程式很龐大。如果某個公司買了這個程式以後,該公司還得招一個人去讀這個程式,當這個人讀懂以後,他又離職了,那公司買這個代碼幹嘛?
2. 代碼的注釋
代碼本身體現不出價值來,有價值的代碼一定是不僅格式非常規範,而且還要有很詳細的設計思路和注釋,這個是很重要的。首先要養成這種習慣,教科書裏面很少講為什麼要做注釋,注釋應該怎麼注。有些人愛在哪兒下注釋就在哪兒下注釋,甚至在語句中間也加,中間也可弄兩個斜杠放兩個花括弧寫點注釋。
注釋格式是非常重要的,但很少有人去注意它。現在的程式如果沒有注釋,則基本上是沒法用的,也就跟你拿一個可執行程式沒什麼兩樣,你拿過來還不能隨便改,你改了後編出來的程式絕對不能用。所以,程式如果沒有詳細的注釋,別人就算拿到了代碼也沒有用,體現不出它的價值來。
Linux是個作業系統,很厲害呀!其實那些程式你拿回來,耐心地去讀它,會發現,它裏面亂得很,那個內核程式除了作者自己能讀懂外,別人可能要花很長的時間才能讀懂。Apache的作者對自己Apache那套代碼是很清楚,但換一個做流覽器的人去讀,也會很困難。一般人只把代碼複製下來後,打個BUILD命令看看能不能正確地編譯,最後能正確編譯的程式就是好的,如果不能正確編譯的程式就刪掉吧,再下載一個,因為他沒有正確的對待代碼的那種思維,而只是認為那代碼本身才有很大的價值,不用關心有沒有注釋。
如果代碼沒有注釋和規範,是沒有價值的,這也是現在為什麼很多的個人跑去賣根源程式的時候,很多的公司都不要。我們不是說沒有技術,任何程式都能做,只是時間的問題,而且像視頻中有的技術,比那些賣代碼的技術還要深得多。真正要做一個有價值的程式,開發程式的思維就很重要,這種思維的具體體現就在注釋及規範的代碼本身。
1.3.2 調試的重要性
調試是很重要的一個部分。所有的程式都是調試出來的,不是寫出來的。講怎麼去調試,實際上就是講一種解決問題的思路。所有的程式寫出來後一定是有問題的,既然有問題,就一定會有一個解決問題的思路。解決問題的方法就是調試的方法。
用VB或者是MFC做出來的程式,先運行一遍看看什麼地方有問題,如果發現有問題,重新改一改,然後又重新運行。這種方法是還沒有入門的調試方法,即是看直接的表像。這種方法既浪費時間,又不能消除隱患。
調試是很重要的內容,如果要進入高深境界,調試是除了瞭解設計程式、平臺以外,一個非常重要的難關。如果要成為高級程式師,就必須過這一關。如果不懂調試,則永遠成不了高手。在學習調試的過程中,對組合語言、體系結構會有進一步的瞭解。
你可能覺得我把調試的作用說得言過其實了,舉例子說明一下吧。請把以下的C程式改寫成彙編代碼:
int i;
extern int In[],Out[];
for(i=0;i<100;i++)
{
Out*=In;
}
我發現90%的人寫出來的彙編代碼可能是不正常的或有錯誤的。要麼是不瞭解32位彙編,要麼是不迴圈,要麼只有迴圈沒有處理等。這是為什麼呢?因為就算是一段小小的代碼,如果沒有經過調試,也可能錯誤百出。
如果你是初級一點的程式師,則如果程式出了問題,也不知道原因所在。怎麼回事呀?我就是搞不清楚。要搞清楚首先要調試,這就涉及到調試的問題。比如說,放到一個檔裏面的,它出錯了,我查程式看了n遍,它就是沒有任何問題,這時候該怎麼辦呢?這時的解決方法就是調試,調試能使得一個程式正常地運轉起來。如果對於程式師來說寫這個程式可能只用了一天的時間,但是調試可能會花他二三天的時間。一個程式絕對是調試出來的,不是編出來的。如果說哪個系統是編出來的,那它肯定會有很多性能方面的問題,包括可能有不可預測的各種各樣的問題。
程式出現問題的話,要能考慮到各種各樣可能的情況,絕對沒有任何臆測。比如,有可能完全是編譯器的錯誤,也有可能因你程式裏面增加了什麼,而對程式產生幹擾,甚至還有一種可能是你的指標基本就沒有給它賦值,指向了別的地方,把別的東西破壞了。這些情況太多了。還有一種常見的錯誤,即MFC裏面很常見的一種設計思維,就是任何一個東西,只管創建,不管釋放、銷毀。這種思路是現在很多程式師做的程式沒用幾下就會死機的原因。這絕對是錯誤的設計思路,而MFC讓你這麼做,就是讓你永遠成不了高手,你寫的程式永遠不可能穩定。
MFC裏面的所有的結構也好,變數也好,只需要你去分配一個,幾乎就不需要你去釋放它。這絕對是錯誤的,程式一定要成對編寫。成對編碼是快速編寫程式的一種方法,而教科書裏面講的那些都是從頭到尾去編。先把那個什麼變數編寫上,再寫第一行,再寫第二行,再寫第三行,最後再寫個大括弧。這種方法絕對是錯誤的。對於現在的程式來說,它效率很慢,沒法即時調試,因為只有最後把所有的程式做完以後,才能進行調試,所以在這中間出現錯誤的幾率就積累得非常大了。

1.4 開放性思維
要具備開放性思維,就必須瞭解包括從CPU的執行方法,到Windows平臺的運轉,到你的程式的調試,最後到你要實現的功能這一整套的內容,只有做到這樣,才能真正提高。如果你的知識範圍很窄,什麼也不瞭解,純粹只瞭解語言,那你的思維就會很狹隘,就會只想到這個語言有這個函數,那個語言沒有那個函數,這個C++有這個類,那個語言沒有這個類等。而真正要做一個系統,思維一定要是全面的,游離於平臺之上的系統和實際的應用軟體是不現實的。
這種所謂理想化,已經有很多人提出是不現實的。所以,任何一個軟體一定都是跟一個平臺相關聯的,脫離平臺之上的軟體幾乎都是不能用的。這就必須對平臺的本身非常瞭解。如果你有平臺這些方面的知識,這樣在思考一個問題的時候,能馬上想到作業系統能提供些什麼功能,我再需要做些什麼,然後就能達到這個目標。這就是一種開放的思維。
在開放的思維下,我要做這個程式的時候,就會考慮怎麼把它拆成幾個獨立的、分開的模組,最簡單的,怎麼把這個模組儘量能單獨調用,而不是我要做個很大的EXE程式。一個很普通的程式師,如果他能夠考慮到將程式分成好幾個動態庫,那麼它的思維就已經有點開放性了,就已經不是MFC那些思維方式了。思考問題的時候能把它拆開,就是說,任何一個問題,如果你能把它拆開來思考,這就是簡單的開放性思維。
但光會拆還是不夠的,儘管有很多人連拆都不會。很多教科書中的程式,要解決問題的時候,就一個main,以後就是一個非常長的函數。這個main函數把所有的事情都解決了。如果連函數都不會分的話,則就是典型的封閉式思維。
這樣的人不是沒有,我是碰見過的。一些畢業生做的程式就有這種情況。所有的問題都由一個函數來解決。他就不會把它拆成幾個模組。我問他,把一件工作拆成幾件模組不是更清晰嗎?他說,拆出來後的模組執行會更慢些。這就是很明顯的封閉式思維和非封閉式思維的區別。
你看MFC的思路,那就是一層套一層的,要把所有的類都實現了,然後繼承。它從CWnd以後,把所有的東西都包括進去了,組成一個巨型的類。這個巨型的類連介面到實現統統包括在裏面。這時你怎麼拆?根本就沒有拆的方法,這就是封閉式思維。
如果一個系統、一個程式不能拆的話,則它基本上是做不好的。因為任何一個程式,如果它本身的複雜度越大,它可能出錯的幾率就越大。比如最簡單的,哪個函數越大,則該函數的出錯幾率就越大。但如果把該函數分成很多小的函數,每個小的函數的出錯幾率就會很小,那麼組合起來的整個程式的出錯幾率就很小。這就是為什麼要把它拆出來的原因。
你用C++來實現的方法也是一樣的。你要把它拆成許多的介面,如果能做到這樣,你就能把它獨立起來,甚至你能把它用動態庫的方法去實現。動態庫是現在的程式非常重要的一塊。
1.4.1 動態庫的重要性
有了動態庫,當你要改進某一項功能的時候,你可以不動任何其他的地方,只要改其中你拆出來的這一塊。這一塊是一個動態庫,然後把它改進,只需要把這個動態庫調試好後,整個系統就可以進行升級。
但如果不是這樣,你的整個程式是獨立的檔,然後,另外的功能也是一個獨立的檔,把這個程式編譯成一個EXE,這就不是動態庫的思想。按道理,我只改這個檔,其他系統也不需要進行調試。理論上看起來是一樣的,而實際的結果往往就是因為你改動了這個檔,使得原來跑得很好的整個系統,現在不能跑了或者出現了很奇怪的現象。如何解釋這個問題?事實上,這就涉及到編譯器產生代碼的方法,如果不瞭解這點的話,永遠找不出問題來。
不存在沒有BUG的編譯器,包括VC,它也會產生編譯上的問題。就算把這些問題都排除,你的軟體也可能因為你加了某些功能,而影響了其他的檔,這個幾率甚至非常大。這又得把你以前的測試工作重頭再來一遍了。
動態庫和EXE有什麼不同呢?
動態庫,包括它的代碼和資料都是獨立的,絕對不會跟其他的動態庫串在一起。但是,如果你把所有功能放到一個EXE的工程裏面,它的資料和代碼就都是放到一起的,最後產生可執行程式的時候,就會互相幹擾。而動態庫就不會,這是由作業系統來保證的。從理論上看,動態庫也是一個檔,我做這個工程的時候也是一個獨立的檔,但它就會出現這樣的問題。
1.4.2 程式設計流程
程式設計流程其實很簡單。第一步就是要拆出模組,如果你有開放性思維,則任何軟體都非常容易設計。怎麼設計呢?首先,拿到問題的時候,一定要明確目標;然後,對作業系統所提供哪些功能,程式怎麼跟作業系統介面考慮清楚;接著,就是“砍”,把它分開,要把它拆成一個個的獨立的模組;最後,再進一步去實現,從小到大地進行設計。
首先“抓”馬上能進行測試的簡單的模組,就像剛才說的成對編碼那樣,寫任何一個部分都要進行調試,每個部分最好能獨立進行調試。這樣,每個部分都是分開的時候,它都有一定的功能。當把所要做的功能都實現後,組合起來,再進行通調就可以了。
決定一個軟體的成敗還是得看該軟體設計的思維是否正確。我們也試過,即使你把那些所謂的軟體寫得再明白也沒有用,如果實現這個軟體的思路不對,則下面的工作根本就沒有必要。
做軟體時,一定要把注釋寫進去。這樣寫成的軟體如果要改版的話,就很容易,因為你的整個系統是開放性的,那麼你要增強某些功能的時候,都是針對其中的某個小項做改進,只要改它就是了。如果那個功能是全新的,則它本身就是一個獨立塊,只要去做即可。
現在很多開發工具都提供了自動化設計的功能,在生成新的程式的時候,只要設置好一些條件,就能自動產生程式的框架,這是一種趨勢嗎?
其實,這種方法不太適用通用軟體的開發,針對某個公司做個ERP系統,可能會管用,但是那些方法拿不到通用軟體裏面來。通用軟體絕對是一行一行地編碼產生出來的,而且每一行編碼的結果要達到一種可預測性。
什麼叫可預測性?就是你寫程式的時候,如果發現某一種症狀,馬上就能想到該症狀是由於哪個地方出了錯,而不是別的地方,也就是從症狀就能判斷出是哪些代碼產生了問題,這就是可預測性。
如果你用MFC來“玩”的話,即使它出錯了,你也可能不知道錯誤在哪里,它的可預測性就很差。做軟體時,如果它的可預測性越高,解決問題的方法就越快。如果某用戶說我出現什麼狀況了,你馬上就可以斷定錯誤,而不用去搜索源代碼,就能想到程式可能是什麼地方有問題,則這就是可預測性。
1.4.3 保證程式可預測性
設計程式的時候,如何保證可預測性呢?答案就是我們上面所說的,所有的代碼必須是經過測試的,必須是一步一步調試過的。只有經過你調試過的代碼,你才能知道這個代碼做某種運算的時候,它是怎樣的執行方法。如果你不知道它的執行方法,你沒進行過調試,則你就沒有任何預測性。要達到可預測性,代碼在彙編級是怎麼執行的,你都得非常清楚。代碼對哪個部分進行了什麼操作,你都得知道。如果達不到這點,你的可預測性就很差。
比如,有些程式,你看它的C或者C++的源代碼時,都看不出任何的問題。你看靜態的程式時看不出任何問題,動態的程式調試你也看不出任何問題,這時,你必須把它的彙編打開,看一看它具體的操作,才能知道。所以說,開放性思維非常重要,你必須從最低層到最上層都要清楚。VC本身提供了一個彙編的調試環境,但是打開彙編後,如果你都看不懂,那你說怎麼調呢?調什麼?如果一個程式經過調試出來,則它會出錯的地方你馬上就會知道,只要看一些表現,就知道它有些什麼問題。
比如說,我們做“大眼睛”的時候有個這樣的現象。當要顯示一個很大的圖的時候,螢幕上只能顯示其中的一小塊,這樣就可能需要拖動整個圖像,但是拖的時候,如果在Windows 2000或Windows XP系統下就會發現,一旦我將圖像拖到右下角時,圖像就一下到左上角去了。該圖像在右下角沒有到底的時候還是顯示正確的,但一旦到底,就把右下角轉到左上角去了,如圖1.2所示。
這是怎麼回事?在Windows 98和Windows 95下,從來沒有這個問題,而且如果圖像不到右下角這一行,只差一點,它也不會出現這樣的問題。為什麼在Windows 98下沒有這樣的問題,在Windows 2000下會有呢?難道是我的程式有問題?

圖1.2 圖像顯示問題示意圖
這時,我就做了一個區域的比較,即看這個區域和整個這個圖像的區域,是否中間運算有錯誤。但程式是調用Windows本身的API,我就懷疑是不是這個API出問題了。於是又重新寫了一個區域相交部分,一步一步去查它,也沒有任何問題,在任何情況下都是好的,但是到達右下角時,圖像就會翻過來。經過以上兩個步驟後,我就能確定,這是Windows作業系統的問題,Windows 98下沒有這個問題,Windows 2000有,Windows XP也沒有改過來。這是作業系統的原因,絕對不是軟體的問題。
為什麼會出現這樣的問題?這是因為微軟設計系統的那些傢夥自以為聰明。只要圖像的左上角是0,不管三七二十一,肯定往下面放,但是它的圖像是正向點陣圖,所有的點陣圖設計的時候是倒過來的。而一個正向點陣圖的高度是負的,否則它顯示的時候是倒過來的。高度是負的時候,這個0發生了變化,從上向下的,那麼他設計作業系統的時候,只看了0而沒去看高度,這時他沒做條件處理。他的想法是為了加速這個點陣圖的速度,是做優化的結果,但結果就出錯了,而到現在他也沒有解決這個問題。
所以,可預測性在這裏就顯得很重要了。當出現這個問題時,能想到要麼就是區域合併有問題,要麼就是直接顯示的這個函數有問題。區域合併的問題可以解決,我寫個函數還不行嗎?我一步一步地去跟蹤,就能肯定這個API有沒有問題,最後得出結論是有問題,也的確是它有問題。如果你不會調試的話,這個問題你永遠也查不出來;如果你不瞭解作業系統,你永遠不會想到作業系統會出問題;如果你不瞭解這個平臺,你根本就不知道問題所在。所以,要成為一個高手,視角一定要從裏到外,從點到面非常開闊。如果你局限在一個封閉的思維裏,做系統就很難。



[如果你喜歡本文章,就按本文章之鮮花~送花給作者吧,你的支持就是別人的動力來源]
本文連接  
檢閱個人資料  訪問主頁  發私人訊息  Blog  快速回覆 新增/修改 爬文標記
ROACH
版主
等級: 30等級: 30等級: 30等級: 30等級: 30等級: 30等級: 30等級: 30
減肥中!請勿餵食

十週年紀念徽章(四級)  

 . 積分: 15118
 . 精華: 14
 . 文章: 11766
 . 收花: 140844 支
 . 送花: 6005 支
 . 比例: 0.04
 . 在線: 8869 小時
 . 瀏覽: 85616 頁
 . 註冊: 8003
 . 失蹤: 3
 . 鄉下地方
#2 : 2005-3-8 10:14 PM     全部回覆 引言回覆

這本書在台灣可以買的到
http://www.opentech.com.tw/search/bookinfo.asp?isbn=9572147145



這篇主題??是否要轉到 『讀書會』??? 感覺起來這篇貼出來後~
越來越覺得這篇應該要貼到『讀書會』



[如果你喜歡本文章,就按本文章之鮮花~送花給作者吧,你的支持就是別人的動力來源]
本文連接  
檢閱個人資料  訪問主頁  發私人訊息  Blog  快速回覆 新增/修改 爬文標記

   

快速回覆
表情符號

更多 Smilies

字型大小 : |||      [完成後可按 Ctrl+Enter 發佈]        

溫馨提示:本區開放遊客瀏覽。
選項:
關閉 URL 識別    關閉 表情符號    關閉 Discuz! 代碼    使用個人簽名    接收新回覆信件通知
發表時自動複製內容   [立即複製] (IE only)


 



所在時區為 GMT+8, 現在時間是 2024-4-28 04:01 AM
清除 Cookies - 連絡我們 - TWed2k © 2001-2046 - 純文字版 - 說明
Discuz! 0.1 | Processed in 0.043070 second(s), 7 queries , Qzip disabled