線上訂房服務-台灣趴趴狗聯合訂房中心
發文 回覆 瀏覽次數:1400
推到 Plurk!
推到 Facebook!

牛人與非牛人的對話 (技術人的故事)

 
jackkcg
站務副站長


發表:891
回覆:1050
積分:848
註冊:2002-03-23

發送簡訊給我
#1 引用回覆 回覆 發表時間:2002-09-28 03:55:34 IP:61.70.xxx.xxx 未訂閱
牛人與非牛人的對話 (技術人的故事) ----"如果你的應用程式不能正確地運行,不要去責怪作業系統。" 2001年,當SUN提出SUN.ONE構架的那一天,XX大學畢業的牛在“牛狼之家” 聊天戰碰到了一個公司的Coder ------------------------------------------------------------------- 牛: 你懂XXX協定、YYY框架、ZZZ思想嗎 coder:稍微知道一點點 牛: 那你看過XX牛的《XXXX》第X版第X卷,YY牛的《YYYY》第Y版第Y卷, ZZ牛的《ZZZZ》第Z版第Z卷嗎 coder:你說的這些書都是《經典書籍》,不過我大都沒認真看過 牛: 這?說,你對XXX協定、YYY框架、ZZZ思想的底層細節應該不是很瞭解哦 coder:可以這?說 牛: 你具體做什?專案, coder:做X2X網站 牛: 你說你不懂XXX協定、YYY框架、ZZZ思想的底層細節,那?你們做X2X網站時, 碰到XXX問題你怎?解決的 coder:很簡單,我們會給XX、YY大學的牛發Email,叫他們給我們解XXX元件。很方 便的。 牛: 如果沒人肯幫你們解XXX元件呢 coder:不會的,每次都有N多牛排長對呢。再說了,到Internet上Search一下,買 XXX元件的公司成堆 牛: 好了,好了,我再問你,你都用什?語言開發呢 coder:用ASP+VB 牛: 你只不知道MS已經不再支援VB+ASP了,改?C#+MS.NET coder:在聊天室裏聽牛說過 牛: 那你?什?還要用VB coder:C#,JAVA我不懂 ,所以我用VB 牛: 唉,又來了,基礎的XXX協定、YYY框架、ZZZ思想的底層細節你說你不太懂, 前沿的C#, MS.NET;JAVA,SUN.ONE你又不懂,你難道沒想過要好好學學嗎 coder:我有想過啊 牛: 那你?什?不學呢 coder:我沒有時間 牛: 你的時間都到哪兒去了 coder:用VB ASP編代碼賺錢啊 牛: 賺錢幹嗎 coder:供我兒子出國讀大學 牛: 讀研究生 coder:不是,是讀本科 牛: 讀本科就出去讀,沒必要吧 coder:在XXX協定、YYY框架、ZZZ思想的底層細節方面,國內經常生?牛的最牛的XX 大學剛剛入門,在****方面連門都沒入。我知道我兒子是塊搞技術的料,所以 我想要讓我兒子系統掌握XXX協定、YYY框架、ZZZ思想的細節,精通前沿的... (聽到Coder批評牛畢業的XX大學,牛有點生氣了,開始不客氣起來) 牛: 你知不知道,你沒有XXX協定、YYY框架、ZZZ思想的底層細節,是寫不出完美 的代碼出來的。還有,像你這樣,雖然現在可以賺一點小錢,但四年後肯定要 被淘汰的...... coder:在我淘汰之前,我就不想幹了 牛: 那你去幹嘛 coder:我想開一家軟體公司,招很多牛,包括精通XXX協定、YYY框架、ZZZ思想的底 層細節的牛,精通MS.net SUN.ONE的牛...... 牛: 好笑! ---------------------------------------------------------------------- 4年後,軟體業VB已經徹底絕?,XXX協定、YYY框架、ZZZ思想的底層細節已經被大量 修改,MS.net和SUN.ONE也快倒掉的時候....... 牛: (XXX公司CTO辦公室裏,看著www.xxx.com上的新聞) 啊! MS.net和SUN.ONE真要倒掉了嗎?看來偶要繼續充電了....... coder:(XXX公司CEO辦公室裏,看著www.xxx.com上的新聞) 哦,MS.net和SUN.ONE果真快倒掉了。看來我要招聘新的CTO和Coder了... 誰也不知道,XXX公司的CTO和CEO就是當年在“牛狼之家”聊天戰聊天的牛和Coder。 很多人自以?什?都知道---的確有很多牛從協定細節到當前潮流到開發環境.... 樣樣都精通,但那是少數---可是卻偏偏不知道自己正真需要的是什?,自己最需要的 又是什?,自己?什?要去知道這?多東西。 有的人知道的的確不多,但是他知道他最需要的是什?。他知道他時間不多,只 能去爭取他最需要的東西。 以後的社會分工會越來越細,沒必要也沒有可能什?都懂,開飛機的顯然不必知 道流體力學---雖然流體力學毫無疑問是飛機飛上天的基礎;裝配飛機的顯然不必知道 採購來的發動機具體是如何把航空油變成動力輸出的----雖然這是飛機可以開動的基 礎。 一樣,用COM 或者EJB元件構造企業系統,你根本沒有必要知道這個COM 或者EJB 元件是如何處理底層TCP/IP連接的。元件生?者關心的是實現細節--穩定性,效率, 安全......至於你,就去關心企業業務流程好了,即使不明白什?是TCP/IP,什? 是IPv6也沒有關係。
------
**********************************************************
哈哈&兵燹
最會的2大絕招 這個不會與那個也不會 哈哈哈 粉好

Delphi K.Top的K.Top分兩個字解釋Top代表尖端的意思,希望本討論區能提供Delphi的尖端新知
K.表Knowlege 知識,就是本站的標語:Open our mind
ccchen
版主


發表:61
回覆:940
積分:1394
註冊:2002-04-15

發送簡訊給我
#2 引用回覆 回覆 發表時間:2002-09-28 12:14:50 IP:203.217.xxx.xxx 未訂閱
可否請你把這些東西貼到"互連園地"
jck1
一般會員


發表:53
回覆:67
積分:24
註冊:2002-05-23

發送簡訊給我
#3 引用回覆 回覆 發表時間:2002-09-28 15:10:28 IP:218.163.xxx.xxx 未訂閱
值得思考文章 我也常再想是不是要學很多的技術 但常常都沒辦法做到 可能是時間不夠 也可能是基礎根本不好 但回頭又看看 如果只是想賺錢的話 好像跟本身的技術沒有決對的關係 因為技術提昇了 公司好像也看不到 雖然你解決事情的方法可能變快變好了 但大部份的公司似乎不喜歡改變現況 除非萬不得以 覺得可能混不下去了 才有可能去改變???????? 所以,學了新技術,可能對己有點用 但公司不見得就要用 不知有無人有同樣的看法呢?? 反正寫程式的日子就是這樣 公司叫你做啥就做啥 除了為了自己的興趣 也不用自己去學什麼新的東西 因為在公司根本就用下上 哎.............
jackkcg
站務副站長


發表:891
回覆:1050
積分:848
註冊:2002-03-23

發送簡訊給我
#4 引用回覆 回覆 發表時間:2002-09-30 20:51:12 IP:61.221.xxx.xxx 未訂閱
與大蝦對話: 領悟設計模式--Template Method / Visitor       [譯者按] 本文根據發表在CUJ Expert Forum上的兩篇文章編譯而成。C/C++ User's Journal是目前最出色的C/C++語言專業雜誌,特別是在C++ Report閉刊之後,CUJ的地位更加突出。CUJ Expert Forum是CUJ主辦的網上技術專欄,彙集2000年10月以來C++社群中頂尖專家的技術短文,並免費公開發佈,精彩紛呈,是每一個C/C++學習者不可錯過的資料。由Jim Hyslop和Herb Sutter主持的Conversation系列,是CUJ Expert Forum每期必備的精品專欄,以風趣幽默的對話形式講解C++高級技術,在C++社群內得到廣泛讚譽。譯者特別挑選兩篇設計模式方面的文章,介紹給大家。設計模式方面的經典著作是GoF的Design Patterns。但是那本書有一個缺點,不好懂。從風格上講,該書與其說是?學習者而寫作的教程範本,還不如說是給學術界人士看的學術報告,嚴謹有餘,生動不足。這一點包括該書作者和象Bjarne Stroustrup這樣的大師都從不諱言。實際上Design Pattern並非一定是晦澀難懂的,通過生動的例子,一個中等水平的C++學習者完全可以掌握基本用法,在自己的編程實踐中使用,得到立竿見影的功效。這兩篇文章就是很好的例證。本文翻譯在保證技術完整性的前提下作了不少刪節和修改,以便使文章顯得更緊湊。    ----------------------------------------------------------    人物介紹:    我 ---  一個追求上進的C++程式師,尚在試用期,聰明但是經驗不足。    Wendy --- 公司裏的技術大拿,就坐在我旁邊的隔間裏,C++大蝦,最了不起的是,她是個女的!她什?都好,就是有點刻薄,              我對她真是又崇拜又嫉妒。    ----------------------------------------------------------    I. Virtually Yours  -- Template Method模式    我在研究Wendy寫的一個類。那是她?這個專案寫的一個抽象基類,而我的工作就是從中派生出一個具象類(concrete class)。這個類的public部分是這樣的:    class Mountie { public:     void read( std::istream & );     void write( std::ostream & ) const;     virtual ~Mountie(); 很正常,virtual destructor表明這個類打算被繼承。那?再看看其protected部分:    protected:     virtual void do_read( std::istream & );     virtual void do_write( std::ostream & ) const;    也不過就是一會兒的功夫,我識破了Wendy的把戲:她在使用template method模式。public成員函數read和write是非虛擬的,它們肯定是調用protected部分do_read/do_write虛擬成員函數來完成實際的工作。啊,我簡直?自己的進步而飄飄然了!哈,Wendy,這回你可難不住我,還有什?招數?儘管放馬過來... 突然,笑容在我臉上凝固,因?我看到了其private部分:    private:     virtual std::string classID() const = 0;    這是什??一個private純序函數,能工作??我站了起來,     “Wendy,你的Mountie類好像不能工作耶,它有一個private virtual function。”    “你試過了?”她連頭都不?。    “嗯,那倒是沒有啦,可是想想也不行啊?我的派生類怎?能override你的private函數呢?” 我嘟囔著。    “呵,你倒是很確定啊!”Wendy的聲音很輕柔,“你怎?老是這也不行,那也不行的,這幾個月跟著我你就沒學到什?東西嗎?小菜鳥。”    真是可惡啊...    “小菜鳥,你全都忘了,訪問控制級別跟一個函數是不是虛擬的根本沒關係。判斷一個函數是動態綁定還是靜態綁定是函數調用解析的最後一個步驟。好好讀讀標準的3.4和5.2.2節吧。”    我完全處於下風,只好採取干擾戰術。“好吧,就算你說的不錯,我也還是不明白,何必把它設?private?”    “我且問你,倘若你不想讓一個類中的成員函數被其他的類調用,應當如何處理?”    “當然是把它設置?private的,” 我回答道。    “那?你去看看我的Mountie類實現,特別是write()函數的實現。”    我正巴不得逃開Wendy那刺人的目光,便轉過頭去在我的螢幕上搜索,很快,我找到了:    void Mountie::write(std::ostream &Dudley) const {     Dudley << classID() << std::endl;     do_write(Dudley); } 嗨,最近卡通片真是看得太多了,居然犯這樣的低級失誤。還是老是承認吧:“好了,我明白了。classID()是一個實現細節,用來在保存物件時指示具象類的類型,派生類必須覆蓋它,所以必須是純虛的。但是既然是實現細節,就應該設?private的。”    “這還差不多,小菜鳥。”大蝦點了點頭,“現在給我解釋一下?什?do_read()和do_write()是protected的?”    這個問題並不難,我組織了一下就回答:“因?派生類物件需要調用這兩個函數的實現來讀寫其中的基類物件。”    “很好很好,”大蝦差不多滿意了,“不過,你再解釋解釋?什?我不把它們設?public的?”    現在我感覺好多了:“因?調用它們的時候必須以一種特定的方式進行。比如do_write()函數,必須先把類型資訊寫入,再把物件資訊寫入,這樣讀取的時候,負責生成物件的模組首先能夠知道要讀出來的物件是什?類型的,然後才能正確地從流中讀取物件資訊。”    “聰明啊,我的小菜鳥!”Wendy停頓了一下,“就跟學習外國口語一樣,學習C++也不光是掌握語法而已,還必須要掌握大量的慣用法。”    “是啊是啊,我正打算讀Coplien的書...”    [譯者注:就是James Coplien 1992年的經典著作Advanced C++ Programming Style and Idioms]    大蝦揮了揮她的手,“冷靜,小菜鳥,我不是指先知Coplien的那本書,我是指某種結構背後隱含的慣用法。比如一個類有virtual destructor,相當於告訴你說:‘嗨,我是一個多態基類,來繼承我吧!’ 而如果一個類的destructor不是虛擬的,則相當於是在說:‘我不能作?多態基類,看在老天的份上,別繼承我。’”    “同樣的,virtual函數的訪問控制級別也具有隱含的意義。一個protected virtual function告訴你:‘你寫的派生類應該,哦,可是說是必須調用我的實現。’而一個private virtual function是在說:‘派生類可以覆蓋,也可以不覆蓋我,隨你的便。但是你不可以調用我的實現。’”    我點點頭,告訴她我懂了,然後追問道:“那?public virtual function呢?”    “盡可能不要使用public virtual function。”她拿起一支筆寫下了以下代碼:    class HardToExtend  { public:  virtual void f(); };  void HardToExtend::f()  {  // Perform a specific action  } “假設你發佈了這個類。在寫第二版時,需求有所變化,你必須改用Template Method。可是這根本不可能,你知道?什??”    “呃,這個...,不知道。”    “由兩種可能的辦法。其一,將f()的實現代碼轉移到一個新的函數中,然後將f()本身設?non-virtual的:    class HardToExtend { // possibly protected     virtual void do_f(); public:     void f(); }; void HardToExtend::f() {     // pre-processing     do_f();     // post-processing } void HardToExtend::do_f() {     // Perform a specific action }    然而你原來寫的派生類都是企圖override函數f()而不是do_f()的,你必須改變所有的派生類實現,只要你錯過了一個類,你的類層次就會染上先知Meyers所說的‘精神分裂的行徑’。” [譯者注:參見Scott Meyers,Effective C++, Item 37,絕對不要重新定義繼承而來的非虛擬函數]    “另一種辦法是將f()移到private區域,引入一個新的non-virtual函數:”    class HardToExtend { // possibly protected     virtual void f(); public:     void call_f(); }; “這會導致無數令人頭痛的問題。首先,所有的客戶都企圖調用f()而不是call_f(),現在它們的代碼都不能編譯了。更有甚者,大部分派生類都回把f()放在public區域中,這樣直接使用派生類的用戶可以訪問到你本來想保護的細節。”    “對待虛函數要象對待資料成員一樣,把它們設?private的,直到設計上要求使用更寬鬆的訪問控制再來調整。要知道由private入public易,由public入private難啊!”    [譯者注:這篇文章所表達的思想具有一定的顛覆性,因?我們太容易在基類中設置public virtual function了,Java中甚至專門?這種做法建立了interface機制,現在竟然說這不好!一時間真是接受不了。但是仔細體會作者的意思,他並不是一般地反對public virtual function,只是在template method大背景下給出上述原則。雖然這個原則在一般的設計中也是值得考慮的,但是主要的應用領域還是在template method模式中。當然,template method是一種非常有用和常用的模式,因此也決定了本文提出的原則具有廣泛的意義。]    ----------------------------------------------------------------    II. Visitor模式    我正在?一個設計問題苦惱。試用期快結束了,我希望自己解決這個問題,來證明自己的進步。每個人都記得自己的第一份工作吧,也都應該知道在這個時候把活兒做好是多?的重要!我親眼看到其他的新雇員沒有過完試用期就被炒了魷魚,就是因?他們不懂得如何對付那個大蝦...,別誤會,我不是說她不好,她是我見過最棒的程式師,可就是有點刻薄古怪...。現在我拜她?師,不?別的,就是因?我十分希望能達到她那個高度。    我想在一個類層次(class hierarchy)中增加一個新的虛函數,但是這個類層次是由另外一幫人維護的,其他人碰都不能碰:    class Personnel { public:   virtual void Pay ( /*...*/ ) = 0;   virtual void Promote( /*...*/ ) = 0;   virtual void Accept ( PersonnelV& ) = 0;   // ... other functions ... };    class Officer : public Personnel { /* override virtuals */ }; class Captain : public Officer { /* override virtuals */ }; class First : public Officer { /* override virtuals */ }; 我想要一個函數,如果物件是船長(Captain)就這?做,如果是大副(First Officer)就那?做。Virtual function正是解決之道,在Personnel或者Officer中聲明它,而在Captain和First覆蓋(override)它。    糟糕的是,我不能增加這?一個虛函數。我知道可以用RTTI給出一個解決方案:    void f( Officer &o ) {   if( dynamic_cast(&o) ) /* do one thing */ else if( dynamic_cast(&o) ) /* do another thing */ } int main() { Captain k; First s; f( k ); f( s ); } 但是我知道使用RTTI是公司編碼標準所排斥的行?,我對自己說:“是的,雖然我以前不喜歡RTTI,但是這回我得改變對它的看法了。很顯然,除了使用RTTI,別無它法。” “任何問題都可以通過增加間接層次的方法解決。” 我噌地一下跳起來,那是大蝦的聲音,她不知道什?時候跑到我背後,“啊喲,您嚇了我一跳...您剛才說什??” “任何問...” “是的,我聽清楚了,”我也不知道哪來的勇氣,居然敢打斷她,“我只是不知道您從哪冒出來的。”其實這話只不過是掩飾我內心的慌張。 “哈,算了吧,小菜鳥,”大蝦斜著眼看著我,“你以?我不知道你心裏想什?!”她把聲音提高了八度,直盯著我,“那些可憐的C語言門徒才會使用switch語句處理不同的物件類型。你看:” /* A not-atypical C program */ void f(struct someStruct *s) { switch(s->type) { case APPLE: /* do one thing */ break; case ORANGE: /* do another thing */ break; /* ... etc. ... */ } } “這些人學習Stroustrup教主的C 語言時,最重要的事情就是學習如何設計好的類層次。” “沒錯,”我又一次打斷她,迫不及待地想讓Wendy明白,我還是有兩下子的,“他們應該設計一個Fruit基類,派生出Apple和Orange,用virtual function來作具體的事情。 “很好,小菜鳥。C語言門徒通常老習慣改不掉。但是,你應該知道,通過使用virtual function,你增加了一個間接層次。”她放下筆,“你所需要的不就是一個新的虛函數嗎?” “是的。可是我沒有權力這?幹。” “因?你無權修改類層次,對吧!” “您終於瞭解了情況,我們沒法動它。也不知道這個該死的類層次是哪個傢夥設計的...” 我嘀嘀咕咕著。 “是我設計的。” “啊...,真的?!這個,嘿嘿...”,我極?尷尬。 “這個類層次必須非常穩定,因?有跨平臺的問題。但是它的設計允許你增加新的virtual function,而不必煩勞RTTI。你可以通過增加一個間接層次的辦法解決這個問題。請問,Personnel::Accept是什??” ”嗯,這個...” “這個類實現了一個模式,可惜這個模式的名字起得不太好,是個PNP,叫Visitor模式。” [譯者注:PNP,Poor-Named Pattern, 沒起好名字的模式] “啊,我剛剛讀過Visitor模式。但是那只不過是允許若干物件之間相互?代訪問的模式,不是嗎?” 她歎了一口氣,“這是流行的錯誤理解。那個V,我覺得毋寧說是Visitor,還不如說是Virtual更好。這個PNP最重要的用途是允許在不改變類層次的前提下,向已經存在的類層次中增加新的虛函數。首先來看看Personnel及其派生類的Accept實現細節。”她拿起筆寫下: void Personnel::Accept( PersonnelV& v ) { v.Visit( *this ); } void Officer::Accept ( PersonnelV& v ) { v.Visit( *this ); } void Captain::Accept ( PersonnelV& v ) { v.Visit( *this ); } void First::Accept ( PersonnelV& v ) { v.Visit( *this ); } “Visitor的基類如下:” class PersonnelV/*isitor*/ { public: virtual void Visit( Personnel& ) = 0; virtual void Visit( Officer& ) = 0; virtual void Visit( Captain& ) = 0; virtual void Visit( First& ) = 0; }; “啊,我記起來了。當我要利用Personnel類層次的多態性時,我只要調用Personnel::Accept(myVisitorObject)。由於Accept是虛函數,我的myVisitorObject.Visit()會針對正確的物件類型調用,根據重載法則,編譯器會挑選最貼切的那個Visit來調用。這不相當於增加了一個新的虛擬函數了嗎?” “沒錯,小菜鳥。只要類層次支援Accept,我們就可以在不改動類層次的情況下增加新的虛函數了。” “好了,我現在知道該怎?辦了”,我寫道: class DoSomething : public PersonnelV { public: virtual void Visit( Personnel& ); virtual void Visit( Officer& ); virtual void Visit( Captain& ); virtual void Visit( First& ); }; void DoSomething::Visit( Captain& c ) { if( femaleGuestStarIsPresent ) c.TurnOnCharm(); else c.StartFight(); } void DoSomething::Visit( First& f ) { f.RaiseEyebrowAtCaptainsBehavior(); } void f( Personnel& p ) { p.Accept( DoSomething() ); // 相當於 p.DoSomething() } int main() { Captain k; First s; f( k ); f( s ); } 大蝦滿意地笑了,“也許這個模式換一個名字會更好理解,可惜世事往往不遂人意...”。 [譯者注:這篇文章我作了一定的刪節,原文中有稍微多一些的論述,而且提供了兩篇技術文章的link。]
------
**********************************************************
哈哈&兵燹
最會的2大絕招 這個不會與那個也不會 哈哈哈 粉好

Delphi K.Top的K.Top分兩個字解釋Top代表尖端的意思,希望本討論區能提供Delphi的尖端新知
K.表Knowlege 知識,就是本站的標語:Open our mind
系統時間:2024-04-26 20:33:52
聯絡我們 | Delphi K.Top討論版
本站聲明
1. 本論壇為無營利行為之開放平台,所有文章都是由網友自行張貼,如牽涉到法律糾紛一切與本站無關。
2. 假如網友發表之內容涉及侵權,而損及您的利益,請立即通知版主刪除。
3. 請勿批評中華民國元首及政府或批評各政黨,是藍是綠本站無權干涉,但這裡不是政治性論壇!