網絡編程到底要怎麼學?

我建議你這麼學:

一、學習方法與內容

1 計算機網絡理論知識

你需要掌握基礎的如三次握手和四次揮手的過程以及各個狀態值,我建議使用 tcpdump 命令實際抓下包就一目瞭然了,然後就是網絡分層,各層的用途,重點熟悉下 TCP/IP 層相關的知識,還有就是 TCP/UDP 的區別,TCP 的滑動窗口機制、擁塞控制算法、TCP 的保序、重傳、確認機制。

學習這些知識的時候,一定不要死記硬背,注重理解。我近來面試了一部分學歷學校非常好的同學,然而,在問到這塊的知識時卻大失所望。例如,有的同學只是單純把三次握手背下來了,我稍微變通一下他就不知道怎麼回答了:

  1. 如果連接一個目標主機不存在的 IP 地址握手過程是怎樣的?連接一個目標 IP 存在但是端口號不存在的主機又是怎樣的握手過程呢?
  2. A 機器上的進程與 B 機器上的進程進行網絡通信,分別經歷了哪些網絡層。

2 Socket 編程本身

Socket 編程你需要先掌握常用的 Socket API,包括但不侷限於:

常用 Berkeley Sockets API 一覽表

學習這些 Socket API 的時候,不是讓你單純地記憶這些函數的參數,而是掌握每一個函數的重難點。

例如:

  1. 如何將一個 socket 設置成非阻塞模式
  2. 阻塞模式下,send 和 recv 函數行爲是什麼樣子的?非阻塞模式下 send/recv 的返回值分別是什麼?
  3. 客戶端發起連接時,如何主動指定通過本地某個端口號去連接?bind 函數如果端口號設置爲 0 是什麼行爲?
  4. listen 函數的 backlog 參數用途是什麼?
  5. 如何實現異步的 connect 函數?
  6. accept 函數調用時,三次握手是否已經完成?
  7. 如何實現半關閉狀態?
  8. nagle 算法的用途是什麼?
  9. select 函數的第一個參數怎麼設置?select 函數的超時參數如果設置爲 NULL 是什麼行爲?

接着要重點學習下常用的網絡模型:

  1. Windows 上常用的網絡模型有 select、WSAEventSelect、WSAAsyncSelect、完成端口模型;

  2. Linux 上常用的網絡模型 select、poll、epoll,epoll 需要重點關注的是水平模式和邊緣模式。

當然,也建議一定要理解,不要死記硬背。C++ 的同學來面試的時候,我會給他們準備如下面試題:

  1. epoll 邊緣模式下,某次讀取了某個 socket 上的部分數據,下次是否會出發讀事件?如果此時又來了一個字節的新數據,是否會觸發讀事件?
  2. epoll 邊緣模式建議儘量一次把數據讀完,怎樣判斷當前數據已經讀完?
  3. epoll 邊緣模式下,對於寫事件應該如何處理?

接着還要熟悉 TCP 協議的流式特性,如何解決粘包問題;還要掌握常見的網絡協議格式,像 HTTP、FTP、POP3/SMTP/WebSocket 協議的格式都建議熟練掌握。

以 HTTP 協議爲例,HTTP 協議包的格式是什麼樣的,包頭和包體如何分界的,GET 與 POST 請求的數據分別放在 HTTP 包的什麼位置,如果放在包體中,如何知道包體的數據有多長。

3 常用網絡命令

學習了常用的網絡命令,可以用來排查網絡故障與定位問題,反過來,也可以加深對網絡理論知識的理解,建議掌握以下命令:ifconfig、ping、telnet、netstat、lsof、nc、curl、tcpdump。

掌握了這些命令要做到學以致用,例如現在某個服務器連接不上,如何使用這些命令判斷是自己網絡的問題還是目標主機的問題;開發了一個服務器程序,手頭上沒有可用的客戶端,如何使用 nc 命令模擬一個;或者反過來,開發了一個客戶端程序,如果用 nc 模擬一個服務器端用於測試。

二、推薦的書籍

  1. 我在我自己的《C++ 服務器開發精髓》一書第四章詳細地總結了網絡編程的二十多個重難點知識,他們可以幫你搞清楚了百分之九十以上的 socket 編程問題,在該書的第五章詳細地介紹了 ifconfig、ping、telnet、netstat、lsof、nc、curl、tcpdump 這些網絡的用戶,推薦一下。

  2. 計算機網絡理論的書推薦《計算機網絡:自頂向下方法》

  3. 網絡編程方面的實戰書來,我推薦韓國人尹聖雨寫的這本《TCP/IP 網絡編程》,這本書也適合無任何 Socket API 編程經驗的小白,這本書涵蓋從基礎的 Socket API 到高級的 IO 網絡模型,有非常詳細和生動的例子。

  4. 等你有了一定的網絡編程以後(熟練使用常見 Socket API),你可以看看遊雙的《Linux 高性能服務器編程》,這本書給沒有基礎的人或者基礎不紮實的人的感覺是,尤其是書的前三章,這書怎麼這麼垃圾,又把網絡理論書上面的東西搬過來湊字數,但是如果你有基礎再按照書上的步驟在機器上實踐一遍,你會發現,真是一本難得的、良心的書,桃李不言下自成蹊吧。如果你掌握了這本書上說的這些知識,你再看陳碩老師的《Linux 多線程服務端編程》或者去看像 libevent 這樣的開源網絡庫,你會進一步的得到提升。

我是程序員小方,一個放浪不羈的程序員,掃碼關注我:

本文由 Readfog 進行 AMP 轉碼,版權歸原作者所有。
來源https://mp.weixin.qq.com/s/F4ri_dX5qgiMCdLS0n6yzA