# 魏小亮:參加編程競賽對實際工作的用處

來源:魏小亮的博客 (opens new window) (作者是Facebook的移動技術總監)、http://blog.jobbole.com/33834/ (opens new window)

有不少的朋友問過這個問題:在中學裡面參加NOI,在大學參加ACM/ICPC,TopCoder,最後對實際工作究竟有多少用處?我把自己的一些理解總結了一下跟大家討論。

我是在94~96年參加NOI和集訓隊,99~2000年參加ACM/ICPC,2002左右玩了半年TopCoder,後來就很少關注編程競賽了,所以可能對近幾年競賽模式的變化不瞭解。另外我目前主要在工業界工作,所以“實際工作”主要指的是在IT工業界的技術型工作。

我想競賽培養的能力可以分成幾個類型:

  1. 基本技術技能。我想參加競賽而且成績不錯的朋友,基本上都有三個非常出色而且難得的基本技術能力:算法設計、快速編程和自我調試。這是所有比賽都必須的: 給定一個問題,需要很快地設計出算法,很快地編寫出程序,並且在整個算法設計和編程過程中不斷拷問自己的設計和程序,儘早發現漏洞、完善設計,最後在提交結果之前通過一系列的測試儘量提高程序通過競賽評委測試的概率。 這三項基本能力是工作裡面非常有用的。 大部分公司的技術面試也集中在這三項基本技能裡面。競賽經驗的確讓優秀的參賽者在實際工作中獲得先發優勢,一般IOI/ICPC/TopCoder的優秀參賽者都很容易獲得公司錄取,並且在起始級別的工程師崗位上作得非常出色。

  2. 獨立學習的能力和自信心。我想大部分的NOI參 賽者都是中學就開始學習中學課程裡面不函括的內容:面向對象程序設計、數據結構、圖論和網絡流理論、算法理論、離散數學等等。如果一個參賽者是通過自己獨 立學習這些課外知識而在競賽裡面脫穎而出的,她一定有獨立學習的能力和自信心,同時相信自己能夠很快的學會各種新知識。這個能力和自信在工作中非常重要:計算機語言日新月異,從Pascal/C到C++/Java到Python/PHP/Javascript/Objective-C⋯⋯一個人不可能從一開始就懂得所有的知識,但只要自信自己能學會任何新的語言和概念(並且的確可以學會),那他就可以敢於面對未知的挑戰。在工作中,這些“敢吃螃蟹第一人”往往會得到更多機會去開發新項目、創建新公司。

  3. 表達能力。這一點我本人在吳文虎老師指導的NOI冬令營裡面獲益匪淺。當時吳老師要求每位冬令營選手挑選一個複雜的競賽問題深入研究解法,最後寫成論文,並且在冬令營裡面做報告。吳老師親自把關,指導論文 裡面寫不清楚或者報告裡面說不清楚的地方。這是我第一次學會如何把一個技術問題寫清楚、說清楚。這樣的訓練雖然跟競賽成績本身沒有直接的關係,但能夠讓競 賽選手的表達能力上了一個台階。表達能力對實際工作有非常重要的意義:現代的大型軟件系統開發不是一個英雄人物就能完成的,如果一個子系統的算法和程序不 能清晰地被理解,那這個子系統和它的作者就成為單一故障點(Single Point Of Failure) —— 只要作者一度假,就沒有人能維護或者擴展這部分。基於這種風險,大家寧願用一個更慢更費內存但能被其他人看懂的解決方案。在這兩年的招聘過程中,我看到不少這樣的可惜例子:不少ACM/ICPC的選手能在15分鐘之內寫出一個很巧妙的算法,在機器上編譯、測試例子都通過。 但在黑板上或程序註釋裡面,他們花20分鐘也沒能說清楚這個算法為什麼是對的,為什麼要用這個算法。

  4. 合作能力:NOI/IOI/TopCoder更多的是單槍匹馬,而ACM/ICPC對合作能力的培養更有幫助。三個編程高手共用一台機器,緊缺資源誰先用誰後用,如何分工,這些問題在實際工作中每天都會遇到,如果一個選手在ICPC裡面學會如何跟隊友協調、如何培養信任,那她在實際工作裡面就很容易融入一個團隊,在團隊裡面找到自己的發力點 ,很快為團隊作出貢獻。

  5. 志同道合的朋友圈:一般來說,願意花額外時間參加競賽的學生都是喜歡寫程序的,因為喜歡,他們往往更容易在這方面越做越好。我10年前在競賽過程中認識的老對手,現在還有很多是好朋友,不時能聯繫一下,得到他們的指導、交換最新的行業信息和趨勢。這一點雖然對實際工作沒有直接幫助,但我覺得是參加競賽獲得的最寶貴的東西。

這些大概是我在比賽裡面學到的最有用的一些東西。下次有時間的時候打算整理一下實際工作裡面有哪些是競賽裡面學不到的。

-----------------------

文章推薦:《編程競賽和邏輯謎題網站大集合》