建模心法(1)——百战不殆是可能的吗?
???????????????????????? 故善戰者,能為不可勝,不能使敵之必可勝。故曰:勝可知而不可為。
????????????????????????????????????????????????????????????????????? ——孫武 《孫子兵法》
????? 我們都知道武功包括招式和心法,二者缺一不可。如果只知招式而不知心法,則招式全無用處。某些特殊情況下可能打出來的是打狗棍法的招式,暗地里卻是在運用全真劍法的心法,這時本質上其實是在使用全真劍法。甚至有的武功,相同的招式卻有兩套心法,應該使用哪一套要視情況而定,如果用錯了心法,不但不能克敵制勝,反而會死得比不會武功的人還慘!
???? ?對于建模這門武功來說,其招式比較簡單,無論是UML圖、ER圖還是數據流圖,頂多個把月就能學會;然而它的心法卻非常高深繁復,要想融會貫通并能根據實際情況運用自如并不容易。基本功法,是要理解什么是模型以及為什么要建模。
什么是模型
????? 模型是對理論、系統或某個東西的有意識的簡化,只關注它們的主要對象或運作方式。模型可以有多種表現方式,它可以是一個仿制品(例如建筑的沙盤模型)、某種表示法(就像我們在中學物理課上學習受力分析時使用的“一個方框代表物體,一個單向箭頭代表受力方向”這種規定)、文字描述、二維或三維的示意圖以及其它任何方便的表達方法。這里有3個要點:
??? ? 1) 模型所表現的對象,可以是某個東西,最常見的是建筑物、汽車、機械等等;可以是一個系統,例如人體系統、一個城市、一個企業、生態環境、一個動物族群、一個應用程序等等;可以是一個理論,例如相對論、進化論、牛頓第二定律等等。
??? ? 2) 模型是對研究對象的有意識的簡化,以便把注意力集中在我們關心的主要對象或運作方式上,并且(更重要的)只有把無關的屬性去掉,才有可能發現可再現的規律(以便對未來的觀測結果作出預測,這也是科學研究的主要目的)。例如牛頓第二定律把物體簡化為一個質點(只關心物體的質量這一個屬性),把空間簡化為平坦的三維空間,把時間簡化為不依賴物體的速度和質量的絕對時間。
????? 3) 模型只存在于我們的腦中,不再具有任何其它(不管在任何意義上)的實在性。模型存在的價值只是服務于某個理論,或者表現某個東西或某個系統的一些我們感興趣的方面。相對論和牛頓第二定律里面的時空模型有很大的不同,不能說這兩個模型哪個更接近于“真實”,它們只是各自適合不同的理論。
建模是必須的么?
???? ?什么簡化啦、抽象啦、概念啦……聽到這些故弄玄虛的詞兒就讓人頭大不已。我們(特別是老板^_^)多么希望今天跟客戶簽了合同,明天,程序員雙手結印,大喝一聲:“啊咪哞咪吽——我是小強——芝麻開門不要錢——”,小宇宙以及查克拉大爆發,然后喀嚓一下子程序奇跡般地就完成了。這個美好的愿望能夠實現么?要回答這個問題,就要先來看看什么是程序。
???? ?程序,是一個系統,它具有一個內部狀態并存在于一個外部環境中,外部環境也有一個狀態。這兩個狀態總是唯一地決定了下一個內部狀態。這個定義里沒有包含結構和行為,我們可以簡單地認為狀態的某些方面可以經驗性地證明是持久的、延續的、不變的,這個穩定的部分為系統的結構,而變化的部分則是行為。可以舉一個簡單的例子,如果我在QQ上對老婆說“我愛你”,我可以預測老婆大人要么收到“我愛你”這三個字,要么啥也收不到,但是絕不會收到“我討厭你”。我為什么能夠預測出老婆可以收到“我愛你”這三個字呢?因為我就是知道——通過連續觀察系統的若干次狀態改變(譬如我發出“我愛你”老婆收到“我愛你”、我發出“我恨你”老婆收到“我恨你”、我發出“我討厭你”老婆收到“我討厭你”),我推斷出QQ系統的規律我發出啥老婆收到啥。外部環境的狀態,除了我(所輸入的字)之外,還包括網絡和老婆的電腦,如果網絡中斷則老婆啥也收不到,如果老婆的電腦里沒裝中文字體則會收到一堆亂碼。值得注意的是,所謂狀態是指如果重現則可以由觀察者再次識別的情形。如果我在觀察QQ系統的狀態變化時加上(老婆收到的信息被儲存的)內存地址這一屬性,則系統的狀態變化就毫無規律可言,我也無法根據系統當前狀態和外部環境的狀態預測系統的下一狀態。事實上,我忽略掉太多東西了,對于系統內部狀態,我忽略掉了老婆收到信息的存儲地址、信息顯示的字體大小等等;對于外部環境的狀態,老婆是男是女、心情如何,天氣是陰是晴、是白天還是黑夜也沒有包括在模型之中。是的,任何對系統的理解都少不了一個模型,即使我們沒有把它畫出來,甚至沒有意識到它的存在。
??? ? 那么把模型畫出來又有哪些好處呢?首先,制作模型是一個強迫思考的過程,這和寫文章是一個強迫思考的過程一樣,園子里的朋友應該都有體會。第二,模型是個很好的思考工具。因為人腦的思考能力非常有限,能同時記住和思考的對象不超過7個,所以邊想變畫,修修改改,要比只在腦子里面默想要有效得多。第三,模型是個有效的溝通工具,有助于消除程序員之間、程序員與領域專家之間的誤解。這一點受到的質疑比較多,有人說UML圖這東西很多程序員都看不懂用戶又怎么能看得懂呢?這確實是個棘手的問題,一種方法是教領域專家看UML圖,當然這要求領域專家夠聰明、愛學習、有時間、感興趣。否則就只有選取或自己發明個領域專家看得懂、感興趣的溝通工具。一般來說信息系統的用戶都是Excel高手,口頭交流、草圖、示例數據都是不錯的招式。
不完全與過于完全
????物理研究上的所有成功,都依賴于對觀察對象的明智選擇。這種選擇,一方面是根據對象的重要程度,另一方面則是根據我們對對象特征的主觀提取。有些特征盡管頗具吸引力,但當前的科學還無力處理,就只好暫時舍棄。
????????????????????????????????????????????????????????????????——詹姆斯·C.麥克斯韋(James C. Maxwell)
????玄之又玄,眾眇之門。
??????????????????? ——老子 《道德經》
????操笑曰:“袁紹色厲膽薄,好謀無斷;干大事而惜身,見小利而忘命。非英雄也。”
????????????????????????????????????????????????????????????????——羅貫中 《三國演義》
??? ? 如前所述,反映系統所有細節的模型沒有意義。模型到底要包括系統的那些屬性,一方面是根據屬性的重要程度,另一方面則是一種主觀提取。“玄之又玄,眾眇之門”并不能作為“道”的模型。“極其玄妙深遠”這種空洞的形容除了增加我們對“道”的敬畏和向往之外,實在沒有更多用處。同樣,沙盤模型只關注建筑物的外觀,除了糊弄一下投資人和購房者,并沒有太大功用。作為袁紹的模型,“色厲膽薄,好謀無斷;干大事而惜身,見小利而忘命”同樣十分簡單,但是可以根據它預測袁紹的行為,所以它是一個好的模型。根據這個模型,曹操做出了很多重要決策,最終在官渡之戰以少勝多,大敗袁紹。
一個模型就是一種理解
??? ? 模型是主觀的。這一結論也許會讓許多人覺得失落,因為這意味著并不存在唯一正確的或者真實的模型。模型既不神秘高深,也不是什么額外的東西,它只是人類理解世界、表達世界的工具。
作為仿真的程序
?? ?? 如果觀察一下我們身邊形形色色的應用程序,可以發現它們大多被用來仿真現實世界,其目的是節約成本。在反恐精英這款游戲里,玩家手持各種流行的槍械進行一場5對5的搏殺,只需十幾分鐘的時間。計算機輔助設計、模擬制造技術早已被廣泛用于機械制造、航空航天甚至仿真鳥巢體育館的鋼架結構,節約的成本數以億計。使用信息系統來仿真企業的實際業務,也是希望以更低的成本、更高的效率完成信息的流動、共享、存儲、處理和檢索。
一個仿真就是對現實世界的一種理解
??? ? 我曾幻想將來可以出現這樣的游戲:它可以完全仿真現實世界里的所有細節。人們進入這個游戲,就如同進入了另一個真實的世界。所以這個游戲不需要人為設計任何情節和角色。對,這個游戲就和《駭客帝國》里面的“矩陣”系統一樣。
??? ? 這樣的游戲有可能被開發出來么?正如我們已經知道的,如果我們關注現實世界里的所有細節,我們就無法得到任何可重現的狀態。同樣,如果游戲仿真了現實世界的所有細節,則我們也無法得到游戲的任何可重現的狀態。那么,我們將永遠也無法證明游戲真的完全仿真了現實世界。
??? ? 就像我們接下來將要看到的,由于我們自身所具有的局限性,無論白箱還是黑箱,都無法做到完全的展現。即使這個系統是我們自己構造的也同樣如此。
火星人 VS 1-2-3
??? ? 我想告訴你,火星人想要入侵地球。他們的飛船已經在近地軌道上飛行了三萬六千八百八十八圈。他們的目的并不是要毀滅地球,而是要把地球作為他們的殖民地。而且,通過觀察,他們發現地球上有一個東西對人類有很強的控制力。火星人相信,只要完成對這個東西的仿真,就可以輕易地奴役人類了。這個東西就是——交通信號燈,俗稱紅綠燈,當然火星人并不這么叫它,不過為了敘述的方便,我們還是統一叫它紅綠燈吧。
??? ? 可是火星人真的要抓狂了。他們不知道紅綠燈到底是如何控制人類的。要搞明白這個問題,他們需要做4項工作:1)確定系統邊界:應該把1個燈泡還是2個燈泡還是3個燈泡作為一個系統來研究?或者應該把一個交通崗的4組紅綠燈作為一個系統?要不要把行人和汽車包括在系統之中?2)選取系統的一些屬性作為研究對象。3)作大量的觀測,歸納系統狀態變化的規律。4)如果找不到規律,或者覺得找到的規律沒啥用,則要重新選取系統邊界和研究對象,也就是重復1)、2)和3)的工作,直到找到滿意的規律為止。這是個漫長的過程,不知何時才能有所突破,然而火星人的時間已經不多了——他們的領導決定把入侵地球的里程碑定在月底。于是,火星人準備找個領域專家來問問,而這個不幸被選中的人就是我。
??? ? 火星人:“你懂紅綠燈?”
??? ? 1-2-3:“我當然懂。”
??? ? 火星人:“給我講講。”
??? ? 1-2-3:“講什么?”
???? ?火星人:“我想仿真一個紅綠燈,然后用它來控制人類。告訴我紅綠燈是怎么控制人類的。”
???? ?1-2-3:“哈!哈!哈!你不會是認真的吧?仿真紅綠燈?還控制人類?”
??? ? 火星人:“我當然是認真的,這個月的獎金就靠它了。”
?? ?? 1-2-3:“可是,我是說,既然你這么聰明——這么高級的UFO也造得出來,為什么還要來問我呢?你只要制作一個和紅綠燈一模一樣的東西就成了。”
??? ? 火星人:“你的意思是說,我只要制作一個東西,它有3個不同顏色的燈泡,以及一個金屬外殼……”
??? ? 1-2-3:“沒錯。”
??? ? 火星人:“那它必須要用電嗎?你知道我們的飛船是不用電這種低效的能源的。”
???? ?1-2-3:“當然要用電,你只要簡單地模仿就行了。”
???? ?火星人:“外殼的顏色呢?也很重要嗎?”
?? ?? 1-2-3:“只是模仿就好。”
????? 火星人:“好吧。那么外殼上面有多少個灰塵和細菌也要模仿么?”
????? 1-2-3:“呃,這個……”
????? 火星人:“外殼的溫度呢?內部的溫度呢?外殼對α和β射線的反射率呢?還有我們發現紅綠燈會輻射2100~7600杰西卡的能量,這能量會造成0.027卡卡西的時空扭曲,而這扭曲又會導致大熊星座λ行星軌道產生2100哞喏的偏離……”
????? 1-2-3:“好吧好吧,我算是服了你了。我直接告訴你好了,很簡單——紅燈停,綠燈行。”
????? 火星人:“哦 哦,原來到底是哪種顏色的燈處于亮著的狀態才是重要的。但是那個黃色的燈是用來干嘛的呢?”
????? 1-2-3:“黃燈只是起一個警告的作用,不是很重要。”
????? 火星人:“嘿嘿,你可不要低估我們火星人的智商哦。那個黃燈無論大小還是位置都和其它的燈一樣,你卻說它一點也不重要,這實在不合邏輯。”
????? 1-2-3:“好吧,我就給你詳細講一講。在綠燈熄滅后,紅燈亮起前,黃燈會亮個十幾二十秒,對于已經過線的行人,它表示:‘即將轉為紅燈,請快速通過十字路口。’;對于尚未過線的行人,它表示:‘請停止通行’。對于交通安全來說它很重要,可是對于你的那個以控制人類為目的的仿真來說就不重要了。要不要仿真它你自己決定吧。”
????? 火星人:“很好,我的仿真的模型也決定了。我們決定忽略行人的移動速度這個屬性,所以我們的模型是這樣的:對于尚未過線的行人,綠燈亮則行,綠燈滅則停;對于過了線的行人,無論如何都要前進。所以我們的模型里只包括綠燈和行人這兩個對象。”
火星程序員
????? 當程序員想要編寫一個針對陌生領域的仿真程序,他的處境不會比火星人強上多少。現實世界對他來說是個黑箱,但是使用黑箱方法進行研究將耗費大量時間且效果不彰。物理學家大多使用黑箱方法研究宇宙,是因為他們找不到上帝來問個究竟。
????? 對于這個領域的領域專家來說,領域是個白箱。領域專家知道領域的所有細節,所有常見與不常見的情況,所有合理與不合理的處理方法。如果存在一個設備,可以把領域專家大腦中的所有領域知識提取出來,那么程序員就可以把領域作為一個白箱來研究了。然而這樣的設備暫時還沒有被研制出來,所以程序員必須具備偵探的本事。通過恰當的提問,敏銳的洞察力,通過大膽的想像和謹慎的求證,程序員得到對領域的深刻理解——領域模型。
????? 但是這模型應該包含領域的哪些方面呢?是工作流程?是數據的流動和對數據的處理?是組織結構以及每個參與者的角色?是重要的事件、事務和時間?是法律、規則和潛規則?是實體和關系?是數據結構和算法?事實上,一個仿真程序幾乎會包含上述所有方面,每個方面都同等地重要,只關注某幾個方面的簡單模型必然失去了其它重要的本質屬性。如果一個模型包括所有屬性又會過于復雜而無法使用一個二維圖形來表達(文字描述也是二維的,所以才會有“說書的一張嘴表不了兩家事”的窘境)。一般的做法是使用若干分別關注某幾個重要屬性的模型分別描述領域,它們最后在程序員的腦子里形成相互關聯的整體認識。
????? 我們將要重點討論的是概念模型——使用合適的(包括創造概念上的)實體和關系來形成概念,闡述領域核心概念和原理的模型。
????? 構建概念模型的目的是作為開發仿真程序的指導。所以從一開始就必須大致知道客戶的需求——程序將為客戶解決什么問題?它將主要仿真現實世界的哪些方面?
????? 仿真程序并不是對現實世界的簡單模仿,它或者比現實世界簡單、或者比現實世界繁雜;或者比現實世界規范、或者比現實世界更加不規范……客戶到底想要的是什么?什么是重要的?什么是可有可無的?這是程序員需要運用偵探技巧重點探索的。
????? 概念模型深刻而簡單。概念模型并不展現所有細節,它展現細節背后的概念和原理。程序員正是通過將模糊概念明確化、隱含概念顯式化,甚至在必要的時候創造概念來逐步取得對領域的深刻理解。
????? 程序員畢竟不是火星人,領域對程序員也不是完全的黑箱。即使是剛剛畢業的大學生,至少也知道什么是漂亮的、舒適的(本能層面);什么是簡便的、有用的(行為層面);什么是禮貌的、友好的(情感層面);什么是合理的、合法的(文化層面)。如果已經開發過別的領域的程序,會發現有一些概念是相通的。這些已知的領域知識對程序員理解新的領域有很大的幫助,并且有助于程序員提出尖銳問題。
變成領域專家還是偵探?
???? 程序員成為領域專家是可能的。有些程序員有條件與某個行業的領域專家長期接觸,甚至就是領域專家的同事。經過幾年甚至十幾年的錘煉,這些程序員的領域知識可以與領域專家媲美,甚至知道的比單個領域專家更多。
???? 另一方面,有些程序員不得不經常對全新的領域建模。他們發展了另一種才能——他們成了不折不扣的偵探。面對陌生的領域知識,千頭萬緒的細節信息,他們一開始會感到心力交瘁、焦頭爛額。但是很快,他們靈光一現,理解了領域中的核心概念,然后慢慢地,一個完整的、深刻的領域模型逐漸浮出了水面。
???? 事實上,并不存在純粹的領域專家型或偵探型的程序員。即使是同一行業,每個客戶的情況都或多或少有些不同;即使是同一客戶,它的業務也在每天悄悄地發生著變化。所以領域專家型的程序員也必須得有點偵探的本事才行。對于偵探型的程序員,正如我們在偵探小說里看到的,出色的偵探都有著豐富的領域知識,他們總是顯得什么都懂,每個細小的領域知識都可能成為破案的關鍵。
實用主義和官僚主義
????? 沒有人喜歡制作模型,就像沒有人喜歡寫文檔。如果每天加班加點的壘代碼都很難按時交付,誰還有心情去弄別的妖蛾子?對于一個程序來說,只有代碼是必不可少的東西,其它的東西都是可有可無的。如果程序員們的腰包都鼓鼓的,時間很充裕,誰不愿把程序弄得跟藝術品似的?但是現實是客戶有壓力、老板有壓力、項目經理有壓力、程序員都在亞健康狀態。建模的好處不過是一張空頭支票,誰知道能不能兌現?
????? 有一些公司特別喜歡制作“正規”的模型,通常他們也喜歡制作大量統一格式的“正規”文檔。他們花大把銀子購買正規的建模軟件,花大量時間畫漂亮的模型。可是,要知道制作文檔所花的時間與這些文檔和程序保持同步的可能性成反比。所以這些龐大的文檔很快就與程序失去了同步,我們稱這些已死的文檔為僵尸模型。一旦模型成了僵尸,所有花在它身上的金錢和金錢買不來的時間就都白白浪費了,剩下來的,就只是漂亮的垃圾而已。當然,有些公司制作文檔的目的是要通過XX認證,或者可以把文檔賣給客戶(確實有這樣大腦袋的客戶),這又另當別論。
????? 我的建議是,只要向前邁一小步就可以了。如果你從未想過細節背后的概念和原理,那么可以嘗試在有空的時候稍微深入想一下下。如果你已在主動思考概念和原理,那么不妨嘗試把它們畫在紙上,看能不能有助于思考?如果你已經把它們畫在了紙上,但是從未把它們與同事和領域專家分享,可以嘗試在下次討論的時候邊說邊畫。如果你真的很閑,可以用專業軟件把它們畫出來。但是不要以為畫出來就萬事大吉了,口頭的講解和討論總是必不可少的。
詳細設計書
????? 在那些需求分析、設計與編碼人員分離的公司,詳細設計書備受推崇。詳細設計書是設計人員與編碼人員之間的橋梁。理論上,詳細設計書包含書寫代碼所需的所有信息,編碼人員不需要對領域有任何的理解,只要按照詳細設計書的要求絲毫不差地編碼即可。這樣,設計人員在設計了一個項目并完成了詳細設計書之后就可以去忙別的項目了。或者設計人員可以遠在天邊(例如外包項目)。但是詳細設計書不可能包含所有細節,實際上是缺少相當多的細節,以至于編碼人員來不及一一詢問設計人員(或者設計人員已經找不到了),這時如果缺少清晰、一致的概念模型,錯誤和混亂就是不可避免的了。如果存在一位天才又勤奮的設計人員,他的詳細設計書百分百的詳細、正確、一致,那么這個詳細設計書不可避免地要多達幾千頁,在這浩如煙海的細節中,編碼人員必然會暈頭轉向,看了前面忘了后面。當然也可能碰巧編碼人員也同樣天才又勤奮,他一字不拉地把這詳細設計書看了N遍,最終融會貫通,完全理解了其中真意。這其實是編碼人員自己從詳細設計書中推導出了概念模型——那為什么要這么麻煩,不一開始就給他一個呢?
百戰不殆是可能的嗎?
????? 正如布魯克斯在他的神作《沒有銀彈》里面所言,由于軟件本身的復雜性和人類自身的局限性,軟件開發工作很難一下子出現質的轉變。但是在量的積累上,我們已經有了很多進展。我是指,幾乎沒有哪個領域沒有仿真程序。有些領域甚至出現了通用產品,并且有了完整的理論。
????? 我們都有這樣的感覺,如果將要開發的軟件已經有了一個使用多年的老版程序,那么工作將會輕松許多。領域專家會稱贊它這里這里設計得非常好用,那里那里爛得不行;這幾個功能每天都得用,那幾個功能幾乎沒用過以及為什么沒用。有了這些信息,再把那個老版程序玩透,就幾乎可以得到對領域全面透徹的理解了。這個老版程序此時就相當于一個原型。
????? 如果雖然這個公司沒有老版程序,但是其它公司已經有了呢?如果已經有大好人把相似領域的概念模型進行了歸納和總結呢?所以,當4年前看到Martin Fowler的《分析模式:可重用對象模型》這本書時,我簡直如獲至寶。可是,4年過去了,這本書我一共看了20頁不到——實在是看不懂哇。是我的實踐不夠?基礎太差?人太笨?心法不對?還是太沒耐心?我不知道……但是我堅信人類能有今天的輝煌書籍功不可沒——別人十幾二十年的思考結果我們十幾二十天就能學到——站在巨人的肩膀上才能更高更遠。我相信對概念模型的歸納、總結和分享可以在很大程度上幫助程序員快速成長。也許,以后大學里也會開設“領域知識”一類的課程。
小結
????? 將油彩隨意地潑灑到畫布上能得到一副畫么?不能。在鋼琴上胡亂按上幾下能得到一首樂曲么?不能。不了解領域知識的程序員能編寫出程序么?能!但是,有多少迷惑就有多少猜測。最為可怕的是這些猜測又會成為其它猜測的根據。結果,使用迭代式開發的項目不多,使用疊加式猜測的項目不少。
????? 但是我們不知道一個好的概念模型到底是什么樣的,也不知道如何把它轉化成實現模型。我們既不知道應該花多少時間在建模上面,也不知道它到底能給項目帶來多大好處。至于是否能保持模型與程序的一致,我們更是沒底。所以,我們最后都放棄了。我們對自己說,跑江湖,混口飯吃而已,還是土辦法最有效。
????? 不過,人類天生就有不斷探索的欲望。我們一直在尋找更有效的工作方法。測試先行?用例先行?要我說,是理解先行!沒有理解,一切都是空談。
????? 所以,不必拘泥于具體的招式。只要足夠重視對領域的理解,不斷探索,我們終究可以找到適合自己和項目組的招式。
下一篇將重點探討具體的構建概念模型的心法。(預計年底發布)
參考文獻
Model. Wikipedia.
Eric Evans, 領域驅動設計(影印版)。人民郵電出版社,2007。
史蒂芬·霍金 著,許明賢 吳忠超 譯,時間簡史(插圖版)。湖南科學技術出版社,2007。
杰拉爾德·溫伯格 著,張佐 萬起光 董菁 譯,系統化思維導論(銀年紀念版)。清華大學出版社,2003。
杰拉爾德·溫伯格 丹尼拉·溫伯格 著,張凱 王佳 譯,系統設計的一般原理。清華大學出版社,2004。
布魯克斯 著,汪穎 譯,人月神話。清華大學出版社,2002。
DONALD A. NORMAN 著,付秋芳 程進三 譯,情感化設計。電子工業出版社,2005。
金庸,神雕俠侶。1976。
?
轉載于:https://www.cnblogs.com/1-2-3/archive/2008/08/04/model-method-part1.html
總結
以上是生活随笔為你收集整理的建模心法(1)——百战不殆是可能的吗?的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 现代中产男人必备的8种气质[zt] 来自
- 下一篇: 关于S3C2440扩展SDRAM的地址连