如何規劃碩士三年的學習生活
結束了為期三個多月的秋招,決定在學生生涯的最後階段對自己的技術棧做一個整理,第一篇首先從碩士三年的學習規劃談起吧。
先做一個簡單的自我介紹,博主本人就讀於上海某高校計算機專業,科班出身。熱愛儲存與虛擬化技術,在相關領域有一定的技術積累,包括資料庫、rocksdb儲存引擎、檔案系統、NVMe driver、虛擬化以及kernel by pass技術。在秋招中有幸獲得阿里、騰訊、百度、Intel、網易互娛、金山雲等公司的offer。
“凌一”是為自己將來入職阿里雲起的花名(不過估計已經被佔用了),其寓意一是指“會當凌絕頂,一覽眾山小”,告訴自己要不怕困難,努力向上攀爬,只有克服一切艱難,才能看到最美的景色;其二是指計算機中的“01”,讓自己在工作學習中要站在計算機的角度來思考問題。在此希望能夠為未來的同學介紹一些碩士期間的學習路線,希望大家能夠有效利用三年的學習時間,積累自己的技術棧。
1. 確立目標
大家剛入學,首先要對自己未來三年後的規劃有明確的目標。對於一般人來說(對於一些大神除外),無非主要關注兩種選擇,一是未來能夠加入到喜歡的公司繼續搬磚(工程型),另外一種是希望能夠繼續讀博士,參與最前沿的科研,將來能夠將自己的學術成果發表在頂會上(學術型)。只要大家能夠確定自己的目標,制定相應的學習計劃,堅持下去,就一定會有收穫。當然,在自己剛入學還在迷茫時候,可以試著嘗試先選定一個努力的目標,只有試了才知道自己適不適合。博主本人屬於工程學術兼備型,碩士期間三篇paper,在工程上也有一定的自我實踐。具體的學習規劃後面將詳細介紹。
2. 制定規劃
在這不具體介紹每個專業的學習規劃是什麼,因為計算機方向實在太多了,對於每一個方向都要涉及到特別多的技術積累,在這是講不清的,況且博主對其它方向也不是特別熟悉。在這裡主要告訴大家,該如何摸索自己的學習規劃,坦白的說,就是在這個方向上我如何學哪些東西,才能在將來秋招大隊中顯示出自己獨特的地方。在此以博主自己的“儲存”方向為例,來說明如何摸索。
基礎知識
基礎知識相當重要,主要是計算機相關的必須課,如語言相關、資料結構、作業系統、資料結構、計算機網路等。基本上對於所有的計算機方向來說,都離不開上述基礎知識。雖然說把這些學好,貌似還做不了什麼成就出來,但沒有這些基礎知識是萬萬不能的。然而,大多數同學對基礎知識還有很大的誤區,認為所從事的工作就是以語言劃分為主的,本科加碩士七年時間,只要熟練掌握一門語言,例如Java,未來就能勝任一份工作,這是遠遠不夠的。程式語言是計算機學科中最重要的一項基礎知識,也是做其它事情的先前條件。就好像剛出生的小孩子一樣,學會了走路說話,似乎還不能自己獨立做一些事情,然而如果連說話走路都還沒有達到的話,還說明還是需要很多的時間來成長的。其實程式語言是大二就應該熟練掌握的知識,而且至少需要會三種不同的程式語言。個人認為,語言只是基礎,必須熟練掌握,沒有哪個語言好,哪個語言不好。各類程式語言(C/C++、Java、Python、Shell、Golang等)都是相通的,不存在會不會的問題,團隊需要什麼,老闆需要什麼,大家就用什麼,即使不熟悉的,看個兩三天基本就應該可以上手工作了。
以儲存方向為例,這是我遇到的各種程式語言的使用場景:
C:底層基本都是用C寫的(例如檔案系統、driver),C是我個人使用最多的語言。
C++:由於喜歡鑽研資料庫的原始碼,因此如果要自己動手修改SQL/">MySQL核心、Rocksdb引擎等,都必須掌握C++。否則原始碼看不懂,自己改核心也無從下手。
Python:因為在論文中,博主經常會遇到一些演算法方面的研究,因此在模擬各類不同的演算法時,經常會選用Python最為測試語言。
Shell:由於經常操作Linux,對於一些經常使用的整合測試,都會手寫shell指令碼來完成。並且針對一些有規律的重複性操作,自己經常會寫一些shell指令碼來控制,大大提高了自己的工作效率。
Golang:由於在深圳某T公司實習的時候,專案需要優化Kafka的客戶端,因此使用golang進行重構,雖然之前沒接觸過golang,但看了一天教程,基本第二天就直接開始用golang來coding了。
此外還有資料結構、作業系統等,此處不再多敘述,如果在基礎知識方面還很欠缺的話,建議多花額外的時間補習。
必備工具
熟練掌握各類工具真的是事倍功半。最早的時候沒有在這方面投入很多精力,導致失去了很多東西。因此建議大家在自己方向上的必備工具一定要花時間去學習,這是未來在效率上和別人競爭的神器。下面還是以我的專業"儲存"方向為例,來說明工具的重要性。
在做儲存相關的技術時,經常會遇到行一些奇葩的bug,例如I/O hang,segmentation fault等。此外,儲存方面大部分的主要關注點是效能的提升,因此不同的型別的效能評估測試也是必備項。此外,對於經常寫程式碼的同學來說,好的編輯器,例如vim,各種除錯、測試工具都是必不可少的。
- fio: 大名鼎鼎的fio,用來直接評估裸盤以及檔案系統的I/O效能。
- perf:可以用來生成火焰圖分析程式中的熱點函式以及CPU使用率等,直觀的分析出程式中的瓶頸以及問題所在。
- cgroup:在做效能評估的時候,經常會遇到為了達到真實的使用場景,用於一些資源限制,系統資源分配管理的工具。
- gdb:Linux下程式設計,尤其是系統軟體,都離不開gdb的除錯。尤其經常遇到segmentation fault的時候。熟練的使用gdb決定了debug的速度。
- valgrind:程式檢測工具,就算再嚴謹的人,難免會遇到一些疏忽的意向不到的錯誤,例如memory leak。因此,熟練使用這類工具能夠保證程式碼的質量,提前解決一些意想不到的bug。
- vim:vim真的是特別強大的編輯器,尤其是在Linux環境下工作的同學,vim的常用配置方法以及各種快捷鍵都是必須要熟練掌握的技術。
此處不再一一介紹,主要是向大家說明工具的重要性。
提升階段
在有了牢固的基礎知識以及熟練掌握各類神器工具之後,後面需要開始進階學習,並不斷的動手提升自己。
首先是基本的進階,就是一些常見的演算法與程式設計。建議可以通過在各類程式設計平臺上動手練習(例如leetcode),一是鍛鍊自己的演算法思維以及語言的熟練度;其次是學習其它大神的寫程式碼規範。如果能夠堅持一到兩年,每天至少一道題的話,會有很大的提高,這個過程是量變到質變的過程。
其次是閱讀學習一些優秀專案的原始碼,如果能夠將一個專案理解到一行行程式碼程式的話,才是真正的學習到其精華,並且能夠加深對其的認識。例如,我們都學過作業系統,知道作業系統基本的執行緒管理、記憶體管理、I/O系統等。但都是理解在檔案概念的層面,如果能夠深入核心原始碼,去細細品味每一個子模組,每一個數據結構的話,對個人的技術來說是很大的提升。例如,在博主大四的時候,便開始閱讀Linux核心檔案系統與記憶體管理相關的原始碼。當然,當你第一次看這麼龐大的專案的時候,一定是一臉懵逼,不知所云。所有人都會經歷從不會到會再到精通的過程,沒有人第一次看就能直接看懂的。我們要做的是,堅持不懈 。在別人看電視劇的時候,我們在看原始碼,在別人玩遊戲的時候,我們還在看原始碼,在別人逛淘寶的時候,我們還在看原始碼。所以當別人在最後抱怨太難放棄的時候,你基本已經上道了。
博主在碩士期間精讀過多個優秀專案的原始碼,ext4、blobstore、Redis、Rocksdb、SPDK、DPDK等。
進階學習
要想在相關領域內學習到最前沿的技術,個人認為有兩個最佳的渠道。一是各類開源社群,二是各類計算機頂會的論文。
首先從開源社群談起,雖然我國網際網路的發展,越來越多的大公司開始倡導去IOE,因此隨之而來的是各種開源專案的不斷崛起。而且越來越多的企業開始使用開源軟體作為底層服務軟體,並且為了更夠更加匹配公司的實際業務環境,越來越多優秀的開發者加入到開源社群當中來。因此,為了學習到這些新技術的發展方向,要時長關注各類社群的動向,最好能參入其中。首先,若想了解到更多的未來發展方向,可以訂閱社群的mailing list,看社群中的大牛經常會提出什麼討論,新的patch等。其次,再不斷的學習相關原始碼的時候,試著做一些優化,可以向社群提patch,來參與其中。對於大家來說,這個剛開始不容易上手,可以選擇先從文件和註釋做起,比如有一些文件寫的不夠全面、不夠規範,或者有一些必要的地方缺少註釋說明,這些都可以作為一個貢獻去向社群提request。在逐漸的更加熟悉後,可以經常關注該專案的github issues,看是否有一些bug需要解決,可以嘗試幫著社群解bug,其次也可以針對一些該專案缺少的功能,自己進行開發,向社群做貢獻。這是一個很好的學習路徑。
其次是各類計算機頂會。各大公司和名校的最新research都會發表在一些好的計算機會議上。要經常關注每年的會議,精讀自己感興趣領域的最新研究。例如,博主是學儲存方向的,因此經常會關注一些系統和資料庫方面的會議,例如FAST、OSDI、VLDB、USENIX ATC等。例如,經常閱讀這些頂會的論文,你將會發現,如今LSM Tree、使用者態軟體棧、Open Channel SSD、RDMA、NVDIMM等,都是目前近幾年無論在企業界還是學術界都特別關心的技術。通過閱讀學習這些優秀的論文,一是能夠學習到其中精妙的系統設計,二是能夠學習到很多表達的技巧(包括presentation、做PPT、畫各類圖等),這些積累都是特別重要的財富。
其次,無論是參與到開源社群中,還是精讀論文,都需要有一個良好的英語基礎。無論是閱讀、寫作、還是聽力和口語都是必不可少的。因此,每天留出額外的時間去學習英語是比不可少的。博主本人在這方面就有些缺失,因此目前仍在不斷努力加強中。
4. 核心競爭力
確立了目標與學習計劃是遠遠不夠的,態度決定一切。最主要的還是腳踏實地,一步步地去學習。當然,學習的過程中難免會遇到很多困難,最主要的還是堅持不懈,勇敢的去戰勝困難。要向優秀的人看齊,不要被外界的東西所打擾。例如,書還沒看兩頁,就去打遊戲了。剛配了一個環境,遇到點困難就放棄了,轉身去看電視劇了。這樣是萬萬不能的。
要有堅定的和果斷的意志。以博主本人碩士期間的生活舉例,通常週中晚上都是12點、1點睡覺,早上一般都是7點吃過早飯就坐在實驗室了。中途從不玩手機、不打遊戲、不看劇、不逛淘寶的。但是週末喜歡出去瘋玩兩天,週末除了特殊情況需要加班加點趕論文外,一般情況週末是不去實驗室的。因此,可以做到勞逸結合。但個人非常喜歡技術,曾經,修改一個開源專案,自己琢磨到半夜,在遇到問題真的很難過,但在自己的堅持下,當新的功能可以完全跑起來的時候,半夜回去趟下都激動不已,難以入眠。