Q&A
在最後一次課上,我們回答了一些學生提出的問題:
- 關於學習作業系統相關題目的建議,如行程,虛擬記憶體,中斷,記憶體管理
- 最適宜早先學習的工具有哪些?
- 我該使用 Python 還是 Bash 腳本還是其他語言
source script.sh
和./script.sh
有什麼區別- 各種程式套件和工具的儲存位置是什麼?如何引用它們?
/bin
和/lib
又是什麼? - 我應使用
apt-get install
還是pip install
來安裝一個 python 程式? - 提升程式碼效能最簡單好用的分析工具有哪些
- 你在用什麼瀏覽器外掛
- 還有哪些有用的資料預處理工具
- Docker 和虛擬機器有什麼區別
- 每個作業系統的優缺點是什麼,我們如何在它們之間進行選擇(例如,為我們的目的選擇最適用的Linux發行版)?
- Vim 還是 Emacs
- 有哪些機器學習的注意與技巧
- 還有什麼 Vim 小技巧
- 雙重驗證(2FA)是什麼,我該如何使用它
- 對Web瀏覽器之間的差異有何評論
關於學習作業系統相關題目的建議,如行程,虛擬記憶體,中斷,記憶體管理
首先,我們不確定你是否真的需要非常熟悉這些,因為他們是非常底層的題目。 如果你要開始編寫底層程式碼,如實現或者修改核心時,它們會比較重要,否則除了課上簡單瞭解的那些之外,這往往不相干。
關於這些的學習資源:
- MIT’s 6.828 class - 碩士級別的作業系統課程。課程是公開的。
- 由 Andrew S. Tanenbaum 寫就的 Modern Operating Systems (4th ed) 良好地概述了上面的概念。
- The Design and Implementation of the FreeBSD Operating System - 關於 Free BSD 的良好資源(注意不是Linux)。
- 其他類似於 Writing an OS in Rust 的指南,人們用各種語言逐步實現核心,一般出於教學目的。
最適宜早先學習的工具有哪些
一些適合學習的內容:
- 如何多使用鍵盤,少使用滑鼠。可以嘗試多加利用快捷鍵,改變介面等方法實現。
- 學好編輯器。你大部分時間都在編輯檔案,非常值得去學習這些能力。
- 學習如何自動化或簡化重複性工作,這將節約大量時間。
- 學習 Git 等版本控制工具,以及如何將它們與 Github 結合,以便在現代軟體專案中協同工作。
我該使用 Python 還是 Bash 腳本還是其他語言
大部分時候,bash 腳本適宜一次性的簡短工作,比如你想要執行一系列指令的時候。bash 腳本有一些奇怪的地方,讓大型程式和腳本難以用 bash 實現。
- bash 可以獲取簡單的使用範例,但是很難獲得全部可能的輸入。例如腳本參數中的空格會導致其出錯
- bash 不適合程式碼重複使用,因此你以前編寫的程式祖堅很難被重用。而且,Bash 沒有庫這種概念。
- bash 依賴例如
$?
或者$@
這些奇妙字串來指代指定值,而其他語言則顯式地引用它們,例如使用exitCode
或sys.args
。
因此,對於大型和/或更複雜的腳本,我們建議使用更成熟的腳本語言,比如 Python 或者 Ruby。 你可以找到人們為了解決這些語言的常見問題而編寫的無數線上資料。 如果在某種語言裡你找到了實現某種特定需求的庫,通常最好的辦法就是使用這種語言。
source script.sh
和 ./script.sh
有什麼區別
在兩種情況下,在 bash 會話中都會讀取並執行script.sh
,不同之處是哪個會話在執行指令。
對於 source
指令是在當前的bash會話中執行的,因此在其執行完畢後,對當前環境的任何更改,比如更改路徑或定義函式,都會在當前會話中保留。
當如同 ./script.sh
這樣單獨執行腳本時候,當前的 bash 會話會啟動一個新的 bash 例項,然後這個例項會執行 script.sh
中的指令。
因此,如果 script.sh
更改了路徑,新的 bash 例項會更改,不過一單退出並且將控制權返回給父 bash 會話,父會話會保留在同一位置。
同樣,如果 ./script.sh
定義了要在終端中訪問的功能,要對其執行 source
。否則在你執行它時,新的 bash 程序將處理函式定義,而不是當前的 shell。
各種程式套件和工具的儲存位置是什麼?如何引用它們? /bin
和 /lib
又是什麼?
根據你在終端執行的程式,這些套件和工具會在你的 PATH
環境變數列出的地方找到。你可以使用 which
指令 (或者 type
) 來檢查你的 shell 在哪裡找到了這個程式。
通常,特定種類的檔案儲存有特定規範,檔案系統階層標準詳細介紹了這些。
/bin
- 需要在單使用者模式可用的必要命令(可執行檔案)/sbin
- 必要的系統二進位檔案/dev
- 必要裝置/etc
- 特定主機,系統範圍內的設定檔/home
- 使用者的家目錄/lib
- /bin/ 和 /sbin/中二進位檔案必要的庫檔案。/opt
- 可選應用軟體包/sys
- 系統資訊與配置檔案 (在第一課中講到過)/tmp
- 臨時檔案(同 /var/tmp),在系統重新啟動時目錄中檔案不會被保留。/usr/
- 用於儲存唯讀使用者資料的第二層次,只讀/usr/bin
- 非必要可執行檔案/usr/sbin
- 非必要的系統二進位檔案/usr/local/bin
- 使用者層級,編譯好的程式
/var
- 變數檔案——在正常執行的系統中其內容不斷變化的檔案
我應使用 apt-get install
還是 pip install
來安裝一個 python 程式?
這個問題通常沒有合適的答案。這與使用作業系統套件管理系統還是特定語言的套件管理系統這個更打的問題有關。你需要考慮這些事情:
- 常見的套件都可以通過這兩種方法獲得,但是不常見或者較新的套件可能不在系統套件管理系統中。這種情況下,使用特定語言的管理系統是更好的選擇。
- 同樣,特定語言的管理系統提供的套件通常更新。
- 當使用系統套件管理系統時,會在系統範圍內安裝。這意味著如果你出於開發目的需要不同版本的庫,系統套件管理系統可能不會滿足你的需求。對於這種情況,大部分程式語言都提供了隔離或虛擬環境,因此你可以使用特定語言的管理系統安裝不同版本的庫而不會發生衝突。對於 Python, 使用 virtualenv;對於 Ruby,使用RVM。
- 取決於作業系統和硬體結構,一些套件可能會以二進位形式存在,或是需要被編譯。例如,在 Raspberry Pi 等 ARM 裝置上,系統套件管理器可能會使用二進位套件,而特定語言的管理器則需要編譯。此時系統管理器往往較優。這很大程度上取決於你的特定設定。
你應該嘗試使用一種解決方案,而不是同時使用兩種,以避免難以除錯的衝突。 我們建議儘可能使用特定於語言的管理系統,並使用隔離的環境(比如 Python 的 virtualenv)來避免汙染全域。
提升程式碼效能最簡單好用的分析工具有哪些
最簡單且十分有效的工具是 print timing。 你僅需手動計算程式不同部分消耗的時間,並重複這個過程,透過二分搜尋法找到耗時最長的部分。
若想尋找更高階的工具,Valgrind 的 Callgrind 可以使你執行程式並計算所有的時間花費,並列出所有呼叫堆疊,即哪個函式呼叫了另一個。然後,它會生成帶註釋的程式碼,其中包含每列消耗的時間。但是它會拖慢程式速度一個數量級且不支援多執行緒。
還有 perf
工具和其他語言的特定取樣分析器可以迅速給出資料。 Flamegraphs 是對取樣分析器的視覺化工具。你還可以使用針對特定語言或任務開發的工具,例如,對於網頁開發,Chrome 與 Firefox 內建的開發者工具有出色的效能分析器。
有時候,程式最慢的部分是系統等待讀取硬碟或網路包。此時,需要檢查根據硬體效能估計的理論速度是否與實際速度相符。也有專用工具來分析系統呼叫中的等待時間,比如用於跟蹤使用者程式內核的 eBPF。如果需要底層的效能分析,bpftrace
是個好選擇。
你在用什麼瀏覽器外掛
以下是我們喜歡的外掛,多數與安全性和易用性有關:
- uBlock Origin - 這是一個用途廣泛 的封鎖器。它可以阻擋廣告與所有種類的第三方互動。它也可以阻擋頁內腳本與其他型別的資源載入。如果你願意花些時間配置來讓他工作地更好,嘗試中等模式或者嚴厲模式。這些設定會在你完成配置之前阻止一些站點正常工作,但是會顯著提升安全性。或者,簡單模式作為預設已經足夠優秀,並能阻擋多數廣告與追蹤。你也可以自訂規則來攔截頁面內容。
- Stylus - Stylish 的一個分支 (不要使用 Stylish,它會 偷竊使用者瀏覽記錄),它允許你旁載入自訂 CSS 樣式。你可以利用 Stylus 輕鬆更改網頁外觀。它可以刪除側邊欄,更改北京顏色,甚至更改文字大小與字型。這對於提升你常訪問的網頁的可讀性非常有用。此外,Stylus 支援其他使用者釋出在 userstyles.org 上的樣式表。例如,多數常用站點都有一個或多個深色樣式。
- 全頁面捕獲 - 在 Firefox 中內建,且有適用的 Chrome extension。這讓你可以擷取全頁面截圖,在用作參考時通常比印出來要好得多。
- Multi Account Containers - 允許你將 cookies 分離至單獨的“容器”,使你可以以不同的身份瀏覽網頁和/或確保站點之間無法共享訊息。
- 密碼管理器整合 - 多數密碼管理器都會有瀏覽器擴充來幫助你輸入憑據,它們方便又安全。比起單純複製-貼上你的名稱與密碼,這些工具會線確認網頁域名與庫中匹配,阻止假站點竊取登入憑據。
還有哪些有用的資料預處理工具
有些資料整理工具由於時間緊湊,在資料預處理課上我們沒有提及。包括 jq
與 pup
這些分別用於 JSON 和 HTML 資料的專有解析器。Perl 程式語言也是適用於高階資料整理的管道工具。還有一個技巧是使用 column -t
指令,將不一定對齊的空格分隔文字轉化成對齊的文字。
通常來說,Vim 和 Python 也可以看作不常規的資料整理工具。對於一些複雜的多行轉換,Vim 巨集是非常寶貴的工具。你可以記錄一系列動作,並根據需求重複多次。例如,在編輯器章節的 lecture notes (和去年的課程回放)中,有一個示例,僅使用vim巨集將XML格式的檔案轉換為JSON。
對於通常以CSV格式表示的表格資料,pandas Python庫是一個很好的工具。 因為它不僅使定義復雜的操作(如分組,聯接或過濾)變得非常容易;而且還很容易繪製資料的不同屬性。它還支援匯出為多種表格式,包括XLS,HTML或LaTeX。 另外,R程式語言(可以說是不好的程式語言)具有用於計算資料統計資訊的許多功能,在作為管道的最後一步時非常有效。 ggplot2是R中不錯的繪相簿。
Docker 和虛擬機器有什麼區別
Docker基於一個名為容器的更通用的概念。容器與虛擬機器之間的主要區別在於,即使核心與主機相同,虛擬機器也將執行整個OS堆疊,包括核心。與其不同,容器避免執行內核的另一個例項,而是與主機共享核心。在Linux中,這是通過稱為LXC的機制來實現的,它利用一系列隔離機制來啟動一個程式,該程式認為其在自己的硬體上執行,但實際上與主機共享硬體和核心。因此,容器的開銷要低於完整的虛擬機器。 另一方面,容器的隔離性較弱,只有在主機執行相同的核心時容器才能工作。例如,如果你在 macOS 上執行 Docker,則 Docker 需要啟動 Linux 虛擬機器以獲取初始 Linux 核心,因此開銷仍然很大。最後,Docker 是容器的特定實現,它是為軟體部署量身定製的。因此有一些奇怪之處:例如,預設情況下,Docker 容器在兩次重啟之間將不會儲存任何形式的儲存。
每個作業系統的優缺點是什麼,我們如何在它們之間進行選擇(例如,為我們的目的選擇最適用的Linux發行版)?
即使有很多不同版本的 Linux 發行版,大部分發行版在大多數使用情況下的表現也相當相同。 大部分 Linux 和 UNIX 功能以及內部工作原理都可以在任何發行版中學習。 發行版之間的根本區別是發行版如何處理軟體套件更新。 某些發行版(例如 Arch Linux)使用滾動更新策略,在這種策略中,套件更新激進,也常常導致不穩定的問題。 另一方面,一些發行版(如 Debian,CentOS 或 Ubuntu LTS)發布更新要保守得多,因此通常情況下會更穩定,但要犧牲一些新功能。 我們建議使用 Debian 或 Ubuntu 來獲得輕鬆穩定的臺式機和伺服器體驗。
MacOS 是 Windows 和 Linux 之間的一個很好的折衷方案,它有靚麗的介面。 但是,MacOS 是基於 BSD 而不是 Linux ,因此係統的某些部分和命令會有所不同。 另一個值得一試的是 FreeBSD 。 即使某些程式不能在 FreeBSD 上執行,但與 Linux 相比,BSD 生態系統的碎片化程度要低得多,而且文件更為友好。 除了開發 Windows 應用程式或需要某些僅限 Windows支援的功能,例如對遊戲的驅動支援外,我們不建議使用Windows。
對於雙系統,我們認為最有效的方案是 macOS 的 bootcamp,從長遠來看,任何其他組合都可能會出現問題,特別是將其與磁碟加密等其他功能結合使用時。
Vim 還是 Emacs
我們三個人都使用 vim 作為主要編輯器,不過 Emacs 也是一個很好的替代品,很值得去同時嘗試它們來看看哪個更適合你。Emacs 與 vim 的編輯模式不同,但是這些功能可以通過 Emacs 外掛,例如 Evil 和 Doom Emacs 實現。Emacs 的優勢是了一使用 Lisp 擴充套件。Lisp 是比 vim 預設使用的 vimscript 更優秀的腳本語言。
有哪些機器學習的注意與技巧
此課程的一些經驗教訓可以直接應用於機器學習程式。 與許多科學學科的情況一樣,在機器學習中,經常要進行一系列實驗,並檢視結果是否有效。 你可以使用 Shell 工具輕鬆,快速地搜尋這些實驗結果並以明智的方式匯總它們。 這可能意味著在給定的時間內或使用特定資料集的情況下選擇所有實驗資料。透過使用JSON檔案記錄實驗相關參數,使用我們在本課程中介紹的工具,這可以變得非常簡單。 最後,如果你不使用叢集來處理你的 GPU 相關作業,則應該研究如何使該過程自動化,因為這不僅會耗費大量時間,還會顯著消耗你的耐心。
還有什麼 Vim 小技巧
一點經驗:
- 外掛 - 花些時間去探索外掛。有許多優秀的外掛解決了 Vim 的缺點,或者增加了能與現有工作流結合的新功能。關於這部分,你可以在 VimAwesome 與其他工程師的 dotfiles 中找到優秀資源。
- 記號 - 在 Vim 中,你可以透過
m<X>
將字元X
設定為記號。其後可以使用'<X>
來回到標記位置。這可以讓你在單一檔案內甚至跨檔案迅速定位。 - 導航 -
Ctrl+O
與Ctrl+I
可以在你最近瀏覽的位置間移動。 - 撤銷樹 - vim 對於追蹤變化有非常奇異的機制。不同於其他編輯器,vim 儲存變化樹,因為你在撤銷後做了一些更正,仍然可以透過撤銷樹的導航回到初始狀態。一些外掛可以視覺化撤銷樹,例如 gundo.vim 和 undotree。
- 按時間撤銷 -
:earlier
和:later
可以使用相對時間前後更正,而非逐一修改。 - 永久重做(Persistent undo) 是一個預設不啟用的 vim 內建功能。它會在多次 vim 啟動之間記錄撤銷歷史。透過設定
.vimrc
內的undofile
和undodir
,vim 會為每個檔案記錄更正歷史。 - Leader 鍵 - Leader 鍵是一個通常留給使用者自訂功能的特殊按鍵。通常是由按下後釋放這個鍵(通常是空格鍵)並與其他按鍵組合來實現特殊指令。通常外掛也會使用這些按鍵增加他們的功能,例如,UndoTree 會使用
<Leader> U
來開啟撤銷樹。 - 高階文字物件 - 文字物件例如檢索也可以使用 vim 指令規程。比如,
d/<pattern>
會刪除下移除匹配 pattern 的字串,cgn
可以更改上次檢索的關鍵字。
雙重驗證(2FA)是什麼,我該如何使用它
雙重驗證在密碼之上給予使用者賬戶額外的保護。登入時,你不僅需要密碼,還必須以某種方式“證明”你可以訪問某些硬體裝置。最簡單的情況是接收 SMS,儘管 SMS 已經被證明有安全性問題。一個良好替代就是使用 U2F 方案,比如 YubiKey。
對Web瀏覽器之間的差異有何評論
截至2020年,當前瀏覽器的格局是大多數瀏覽器都與 Chrome 很相像,因為它們使用相同的引擎(Blink)。這意味著同樣基於 Blink 的 Microsoft Edge 和基於 WebKit(與 Blink 類似的引擎)的 Safari 都是 Chrome 的較差版本。就效能和可用性而言,Chrome 是一款相當不錯的瀏覽器。如果你需要替代,建議使用Firefox。在幾乎所有方面,它都可以與 Chrome 媲美,並且它在隱私保護方面也十分出色。 另一個名為 Flow 的瀏覽器尚未完成,但它正在實現一個新的渲染引擎,該引擎有望比當前的渲染引擎更快。
Licensed under CC BY-NC-SA.