0) 先嘮叨幾句
學習 Python 有幾周了,也寫了 2 個小專案來解決自己的實際需求。簡單記錄一下,供自己備忘,也供後來者參考。
0.0) 我為什麼選擇 Python
我之前使用 Swift + Vapor 開發了 iPic (圖床工具) 的後端服務,遇到很多問題:
- 主要還是 Swift 在 Ubuntu 下並不成熟,甚至很多關鍵性、基礎性的庫,都是 TBD;
- 以及,基於 Swift + Ubuntu 的庫並不多,開發起來很吃力。
接下來要開發 Klib (Kindle、iBooks 標註管理) 的標註分享功能,需要後端支援,於是打算好好學一學後端開發。
適合後端開發的語言還是挺多的,比如 Java、PHP、Python、Ruby、Go、Javascript、等等。我其實並沒有嚴格比較,最後選擇了 Python,主要原因其實是和 Swift 相對的:
- Python 成熟,無論在 Windows/Linux/macOS 都很穩定。
- Python 輪子多,幾乎所有能標準化的操作都能找到庫,然後你可以專注於自己的業務。
還有個原因,之前我接觸過的開發語言(VB/C++/Java/C#/Swift)都是編譯型的,這次想學個 解釋型 的玩玩。
0.1) 首先,知道要學什麼
先形而上地聊聊這個話題。
至少從我的經驗來看,在學習一樣新東西時,我很希望能被告知要學什麼,類似於一個大綱、知識點清單。這樣,我就可以對照著清單一樣樣學習,方向感清晰、還不怕走彎路。
而事實上,很少有這樣的「清單」,最接近的可能是書的目錄。可惜,好書實在太少了。尤其技術更新快,書中的知識很可能是陳舊的。
出於這個理解,本文我只會 羅列我學習 Python 時所遇到的知識點,儘量組織成系統的清單。
0.2) 然而,我並不會教你怎麼學
清單上的知識點,我並不打算展開講,因為:
- 這太花(不)時(賺)間(錢)了
- 通常,官方文件已經足夠好,我沒必要複製貼上
所以,對於某一個具體的點,還得你自己去學習。至於怎麼學?我建議,在專案開發實際用到某個點時,再參考官網系統性的學習。
如果你實在急的必須在被炒魷魚之前解決某個問題(通常並不存在),你可以上網搜尋,通常在技術部落格、StackOverflow 這樣的網站上能找到答案。
不過,這是種投機行為、可能會有 陷阱:
- 如果你找對了方案,可能很快就解決問題。
- 可如果你找了過期的、錯誤的、不適合你的環境的方案,你可能會掉入解決 A 問題時遇到 B 問題、解決 B 問題時又遇到 C 問題這樣的陷阱,所花的時間,會當初系統性地學習,更多。
1) Python 語法及基礎
好,嘮叨了半天,終於來乾的了。
1.0) Python 2 or 3?
Python 的 2、3 之爭,在網上可以找到很多。雖然我一向主張學新不學舊(比如我甚至嘗試用 Swift 開發後端,no zuo no die…),但在後端方面,由於吃了 Swift 的虧,我自己選擇先學習 Python 2。真到了不得不用 3 的時,學。據說差別並不大(我保證,絕對沒有 Swift 2 和 3 的差別大)
1.1) 入門教程
雖說我一向建議以官網為基礎學習,但 Python 的官網的文件實在是太長了。沒辦法,為了全面性,各種犄角旮旯、你一輩子都用不到點的,官網也要提及。
這裡介紹 2 個 Python 入門教程:
- 英文:Learn Python the Hard Way
- 中文:廖雪峰的 Python 2.7教程
- 注意,不要學習最後的「實戰」,相信我,至少目前不適合你。
2) 儘早開發 Python 專案
我建議,一旦有了語法基礎,儘早 開發實際的、能解決自己問題的專案(或表述為工程、產品、工具、輪子)。
注意,一定要是「能解決自己問題的專案」。相信我,如果只是做一個你自己根本用著的部落格系統、爬蟲之類的,學習過程中的困難一定會讓你半途而廢的。
2.0) 專案的資料夾結構
如果你真的想寫個好專案,專案的資料夾結果一定要拿得出手,比如要區分程式碼、配置、資料、文件、測試等檔案。尤其對於在不同伺服器上部署、需要區分開發與生產環境的專案,更重要。
注意,資料夾結構並沒有唯一解;並且,和你使用的網路框架(後面會介紹)相關。在實踐中逐漸優化,越早形成一套自己熟悉的專案結構,收益越大。
我在 GitHub 上建立了一個 Python 專案資料夾結構示例,供參考。
參考:
- learnpythonthehardway.org/book/ex46.h…
- python-guide-pt-br.readthedocs.io/en/latest/w…
- github.com/kennethreit…
2.1) 單元測試
單元測試很重要、很重要、很重要。
尤其對於後端程式,幾乎沒有使用者互動,非常適合進行單元測試。也許,一些已經超出了單元測試的範疇,稱之為功能測試、壓力測試、等等更合適。Anyway,叫測試就對了。
我在開發過程中有寫單元測試的習慣,甚至有時會先寫單元測試、再寫功能程式碼(恩,這就是測試驅動開發)。
在多個測試框架中,我目前選擇 pytest:一直在更新、對 Python 3 支援好、自動發現測試用例。
2.2) IDE
我一位大學同學,用 Windows 記事本開發了一個區域網內 IM 工具,可那是為了學習。人生苦短,還是用 IDE 開發吧。
選什麼呢?其實我並沒有糾結,因為之前在 Windows 上使用 Visual Studio、且一直聽聞 Visual Studio Code 不錯,就直接上了 VS Code
不過,VS Code 本身只提供一個框架,要打造適合自己的 IDE,還得有一系列的配置,比如主題、字型、快捷鍵、外掛、等等。
就 Python 開發,目前還有幾點不順手(如果你知道怎麼做,麻煩告訴我):
- 出錯時,不能點選錯誤日誌跳轉至對應的程式碼
- 單元測試有時會卡死,重啟 VS Code 後正常
- 除錯工具跟 Xcode 等工具有差距
- 快捷鍵沒辦法和 Xcode 統一,用起來很割裂
3) 善用 Python 庫
Python 的優勢之一,就是輪子多,也就是庫(模組)豐富。碰到一個問題,你不愁找不到庫,而是不知道該選哪個,甜蜜的煩惱。
號外:我為 Python 造的第一個輪子:AES256CBC
3.1) 標準庫
任何語言都會把常用的庫,納入自己的標準庫中。其實,很多時候我們說一門語言,都是在學其標準庫。
對於標準庫的學習,倒是建議參考 官方文件
3.2) 管理 Python 庫
庫多了,管理就成了問題。這個沒什麼好說的,直接使用 pip
小技巧:
- 對於專案的依賴庫,可以使用 requirements.txt 集中管理。
pip freeze > requirements.txt
pip install -r requirements.txt複製程式碼
- 可以將 Python 的安裝源改為國內豆瓣、阿里等映象源,速度快。
3.3) Python 執行環境
庫+庫,就是 Python 執行環境。尤其,當你需要在伺服器上部署 Python 專案時,保證伺服器和開發環境有一致的 Python 執行環境,很重要。
推薦使用 pyenv,其利用 Shell 的 shims
機制,當你 cd 到專案目錄時,自動切換 Python 版本(對比 virtualenv,其需要手動執行 source 命令,麻煩)。
小建議:要在自己的電腦上特別建立一個「Python 髒環境」,用於平時寫臨時程式碼、測試新模組時使用,確保不會破壞電腦上的 Python 環境。
4) 使用 Python 開發網路服務
前面據說,我學 Python 主要是為了後端。我目前使用的是 Flask + Gunicorn + Nginx + MySQL + Supervisor 組合。
4.0) Flask
Python 的 Web 框架不少,不過據說主要還是 Django 和 Flask。據說:
- Django 的特點的大而全、開箱即用。
- Flask 的特點的小巧靈活、定製性高。
只要不是太不成熟、坑太多,我通常會選擇簡單的,於是,選 Flask.
Flask 是個大話題,根本不適合在這裡介紹,直接看 Flask Web Development 這本書吧,建議讀原文。
4.1) Gunicorn
Flask 自帶的 Web 伺服器只是能讓程式碼跑起來,而真正用於生產,則需要考慮併發、快取等問題。
主要的選擇是 uWSGI 和 Gunicorn,和 Flask 與 Django 的對比很相似:
- uWSGI 的特點的成熟、用的人多、高效能、強大(複雜)
- Gunicorn 則更簡單、易用
於是,選 Gnuicorn.
Gnuicorn 的配置簡單,直接看官方文件即可。
4.2) Nginx
有了 Flask + Gunicorn,為什麼還要 Nignx?職責不同,Nginx 在處理靜態資源、https/http2、負載均衡等方面,更擅長。
Nginx 我就不介紹了吧?主要還是和 Gnuicorn 的配合。
4.3) MySQL
本地測試,我直接使用 SQLite,但要用於伺服器,還是 MySQL 吧。
主要這次開發 Klib 後端服務,業務上的資料比較規整,適合關聯式資料庫;以後有機會再試試 NoSQL 吧。
4.4) Supervisor
服務,要的就是穩定。
啥叫穩定?就是程式掛了能滿血復活、重新執行。
於是,使用 Supervisor,監控程式執行,掛了就立即重新執行。
5) 尾巴
這麼長、這麼枯燥的文章你都能看完?牛!粉我的公眾號吧,以後每週二都會有一篇技術長文。
Python 我只是入門,要學的東西還很多,以後還會有小結、分享。
未完待續…