[計算機網絡] TCP和UDP總結及常見面試題

原文鏈接:https://blog.csdn.net/zhang6223284/article/details/81414149
本文僅作爲個人整理筆記,供個人學習,自用不商用

知識點梳理總結部分

1 TCP和UDP區別

  • TCP是面向連接的,UDP是面向無連接的
  • TCP是可靠的,UDP不是可靠的
    (也就是說,通過TCP連接傳送的數據,無差錯,不丟失,不重複,且按序到達;UDP盡最大努力交付,即不保證可靠交付)
  • TCP是面向字節流的,UDP是面向報文的
  • TCP只支持點對點通信,UDP支持一對一,一對多,多對一,多對多的通信模式
  • TCP首部開銷(20字節)比UDP的首部開銷(8個字節)要大
  • TCP保證數據正確性,UDP可能丟包
  • TCP保證數據順序,UDP不保證

2 UDP

TCP 和 UDP 是傳輸層的兩個協議

我們來看一下 UDP 的包頭
在這裏插入圖片描述
由上圖可以看出,UDP 除了端口號,基本啥都沒有了。如果沒有這兩個端口號,數據就不知道該發給哪個應用。

所以 UDP 就像一個小孩子,特別簡單,有如下三個特點

  • UDP 的特點
  • 溝通簡單,不需要大量的數據結構,處理邏輯和包頭字段
  • 輕信他人。它不會建立連接,但是會監聽這個地方,誰都可以傳給它數據,它也可以傳給任何人數據,甚至可以同時傳給多個人數據。
  • 愣頭青,做事不懂變通。不會根據網絡的情況進行擁塞控制,無論是否丟包,它該怎麼發還是怎麼發

因爲 UDP 是"小孩子",所以處理的是一些沒那麼難的項目,並且就算失敗的也能接收。基於這些特點的話,UDP 可以使用在如下場景中

UDP 的主要應用場景

  • 需要資源少,網絡情況穩定的內網,或者對於丟包不敏感的應用,比如 DHCP 就是基於 UDP 協議的。
  • 不需要一對一溝通,建立連接,而是可以廣播的應用。因爲它不面向連接,所以可以做到一對多,承擔廣播或者多播的協議。
  • 需要處理速度快,可以容忍丟包,但是即使網絡擁塞,也毫不退縮,一往無前的時候

基於 UDP 的幾個例子

  • 直播。直播對實時性的要求比較高,寧可丟包,也不要卡頓的,所以很多直播應用都基於 UDP 實現了自己的視頻傳輸協議
  • 實時遊戲。遊戲的特點也是實時性比較高,在這種情況下,採用自定義的可靠的 UDP 協議,自定義重傳策略,能夠把產生的延遲降到最低,減少網絡問題對遊戲造成的影響
  • 物聯網。一方面,物聯網領域中斷資源少,很可能知識個很小的嵌入式系統,而維護 TCP 協議的代價太大了;另一方面,物聯網對實時性的要求也特別高。比如 Google 旗下的 Nest 簡歷 Thread Group,推出了物聯網通信協議 Thread,就是基於 UDP 協議的
    在這裏插入圖片描述

3 TCP

首先是 TCP 的包頭格式

在這裏插入圖片描述

TCP 的包頭有哪些內容,分別有什麼用

  • 首先,源端口和目標端口是不可少的。
  • 接下來是包的序號。主要是爲了解決亂序問題。不編好號怎麼知道哪個先來,哪個後到
  • 確認序號。發出去的包應該有確認,這樣能知道對方是否收到,如果沒收到就應該重新發送,這個解決的是不丟包的問題
  • 狀態位。SYN 是發起一個鏈接,ACK 是回覆,RST 是重新連接,FIN 是結束連接。因爲 TCP 是面向連接的,因此需要雙方維護連接的狀態,這些狀態位的包會引起雙方的狀態變更
  • 窗口大小,TCP 要做流量控制,需要通信雙方各聲明一個窗口,標識自己當前的處理能力。

通過對 TCP 頭的解析,我們知道要掌握 TCP 協議,應該重點關注以下問題:

  • 順序問題
  • 丟包問題
  • 連接維護
  • 流量控制
  • 擁塞控制

4 TCP 的三次握手

所有的問題,首先都要建立連接,所以首先是連接維護的問題

TCP 的建立連接稱爲三次握手,可以簡單理解爲下面這種情況:

A:您好,我是 A
B:您好 A,我是 B
A:您好 B

至於爲什麼是三次握手,總結的話就是通信雙方全都有來有回

對於 A 來說它發出請求,並收到了 B 的響應,對於 B 來說它響應了 A 的請求,並且也接收到了響應。

TCP 的三次握手除了建立連接外,主要還是爲了溝通 TCP 包的序號問題。

5 TCP 四次揮手

說完建立連接,再說下斷開連接,也被稱爲四次揮手,可以簡單理解如下

A:B 啊,我不想玩了
B:哦,你不想玩了啊,我知道了
這個時候,只是 A 不想玩了,即不再發送數據,但是 B 可能還有未發送完的數據,所以需要等待 B 也主動關閉。
B:A 啊,好吧,我也不玩了,拜拜
A:好的,拜拜

這樣整個連接就關閉了,當然上面只是正常的狀態,也有些非正常的狀態(比如 A 說完不玩了,直接跑路,B 發起的結束得不到 A 的回答,不知道該怎麼辦或則 B 直接跑路 A 不知道該怎麼辦)

6 累計確認

TCP如何實現可靠傳輸?

首先爲了保證時序性,每個包都有一個ID。在建立連接的時候會商定起始ID是什麼,然後按照ID一個個發送,爲了保證不丟包,需要對發送的包都要進行應答,當然,這個應答不是一個一個來的,而是會應答某個之前的ID,表示都收到了,這種模式稱爲累計應答或累計確認。

爲了記錄所有發送的包和接收的包,TCP需要發送端和接收段分別緩存這些記錄,
發送端的緩存裏是按照包的ID一個個排序,根據處理的情況分爲四個部分:

  • (1)發送並且確認的
  • (2)發送尚未確認的
  • (3)沒有發送等待發送的
  • (4)沒有發送並且暫時不會發送的
    這裏的第三部分和第四部分就屬於流量控制的內容

在TCP裏,接收端會給發送端報一個窗口大小,叫Advertised window。這個窗口應該等於上面的第一部分加第二部分,超過這個窗口,接收端就接收不過來了,就不能發送了
於是,發送端要保持下面的數據結構
在這裏插入圖片描述
對於接收端,它的裏面的內容要簡單一些

  • (1)接收並且確認過的
  • (2)還沒接收,但是馬上 就能接收的
  • (3)還沒接收,但也無法接收的

接收端對應的數據結構:
在這裏插入圖片描述

7 順序問題和丟包問題

結合上面的圖看,在發送端,1、2、3 已發送並確認;4、5、6、7、8、9 都是發送了還沒確認;10、11、12 是還沒發出的;13、14、15 是接收方沒有空間,不準備發的。

在接收端來看,1、2、3、4、5 是已經完成 ACK 但是還沒讀取的;6、7 是等待接收的;8、9 是已經接收還沒有 ACK 的。

發送端和接收端當前的狀態如下:

  • 1、2、3 沒有問題,雙方達成了一致
  • 4、5 接收方說 ACK 了,但是發送方還沒收到
  • 6、7、8、9 肯定都發了,但是 8、9 已經到了,6、7 沒到,出現了亂序,緩存着但是沒辦法 ACK。
    根據這個例子可以知道順序問題和丟包問題都有可能存在,所以我們先來看確認與重傳機制。
假設 4 的確認收到了,5 的 ACK 丟了,6、7 的數據包丟了,該怎麼辦?

一種方法是超時重試,即對每一個發送了但是沒有ACK的包設定一個計時器,超過了一定的時間就重新嘗試。這個時間必須大於往返時間,但也不宜過長,否則超時時間變長,訪問就變慢了。

如果過一段時間,5、6、7都超時了就會重新發送。接收方發現5原來接收過,於是丟棄5;6收到了,發送ACK,要求下一個是7,7不幸又丟了。當7再次超時的時候,TCP的策略是,超時間間隔加倍。 每當遇到一次超時重傳的時候,都會將下一次超時間隔設置爲之前的兩倍。

超時重傳的機制使超時週期可能相對較長,是否有更快的方式呢?

有一個快速重傳的機制, 即當接收方收到一個序號大於期望的報文段時,就檢測到了數據流之間的間隔,於是發送 三個冗餘的ACK,客戶端接收到之後,知道數據報丟失,於是重傳丟失的報文段。
例如,接收方發現6,8,9都接收了,但是7沒來,於是發送三個6的ACK,要求下一個是7。客戶端接收到3個,就會發現7的確又丟了,不等超時,馬上重發。

8 擁塞控制的問題

擁塞控制也是通過窗口的大小來控制的,但是檢測網絡滿不滿是個挺難的事情,所以TCP發送包經常被比喻成往水管裏灌水,所以擁塞控制就是在不堵塞,不丟包的情況下儘可能的發揮帶寬。

水管有粗細,網絡有帶寬,即每秒鐘能發送多少數據;水管有長度,端到端有時延。
理想情況下,水管裏面的水 = 水管粗細 * 水管長度,
對於網絡上,通道的容量 = 帶寬 * 往返時延。

如果我們設置發送窗口,使得發送但未確認的包爲通道的容量,就能撐滿整個管道。
在這裏插入圖片描述
如圖所示,假設往返時間爲 8 秒,去 4 秒,回 4 秒,每秒發送一個包,已經過去了 8 秒,則 8 個包都發出去了,其中前四個已經到達接收端,但是 ACK 還沒返回,不能算髮送成功,5-8 後四個包還在路上,還沒被接收,這個時候,管道正好撐滿,在發送端,已發送未確認的 8 個包,正好等於帶寬,也即每秒發送一個包,也即每秒發送一個包,乘以來回時間 8 秒。

如果在這個基礎上調大窗口,使得單位時間可以發送更多的包,那麼會出現接收端處理不過來,多出來的包就會被丟棄,這個時候,我們可以增加一個緩存,但是緩存裏面的包4秒內肯定達不到接收端了,它的缺點會增加時延,如果時延達到一定程度就會超時重傳

TCP擁塞控制主要用來避免兩種情況,包丟失和超時重傳,一旦出現了這些現象說明發送的太快了,要慢一點。
具體的方法就是發送端慢啓動, 比如倒水,剛開始倒的很慢,漸漸變快。然後設定一個閾值,當超過這個值的時候就要慢下來
慢下來還是在增長,這時候就可能水滿則溢,出現擁塞,需要降低倒水的速度,等水慢慢滲下去。

擁塞的一種表現是丟包,需要超時重傳,這個時候,採用快速重傳算法,將當前速度變爲一般,所以速度還是在比較高的值,也沒有一夜回到解放前。

面試問題

9 面試問題

TCP和UDP的區別
  • TCP是面向連接的,UDP是面向無連接的
  • TCP是可靠的,UDP不是可靠的
    (也就是說,通過TCP連接傳送的數據,無差錯,不丟失,不重複,且按序到達;UDP盡最大努力交付,即不保證可靠交付)
  • TCP是面向字節流的,UDP是面向報文的
  • TCP只支持點對點通信,UDP支持一對一,一對多,多對一,多對多的通信模式
  • TCP首部開銷(20字節)比UDP的首部開銷(8個字節)要大
  • TCP保證數據正確性,UDP可能丟包
  • TCP保證數據順序,UDP不保證
什麼是面向連接,什麼是面向無連接

在互通之前,面向連接的協議會先建立連接,如 TCP 有三次握手,而 UDP 不會

  • **面向連接:**是指通信百雙方在通信時,要事先建立一條通信線路,其有三個過程:建立連接、使用連接和釋放連接。電話系統度是一個面向連接的模式,撥號、通知話、掛機;TCP協議就是一種面向連接的協議。
  • **面向無連接:**是指通信雙方不需要事先建立一條通信線路道,而是把每個帶有目的地址的包(報文分組)送到線路上,由系統自主選定路線進行傳輸。郵專政系統是一個無連接的模式,天羅地網式的選擇路線,天女散屬花式的傳播形式;IP、UDP協議就是一種無連接協議。
TCP爲什麼是可靠連接
  • 通過TCP連接傳輸的數據無差錯,不丟失,不重複,且按順序到達
  • TCP報文頭裏面的序號能使TCP的數據按序到達
  • 報文頭裏面的確認序號能保證不丟包,累計確認及超時重傳機制
  • TCP擁有流量控制及擁塞控制的機制
TCP協議如何來保證傳輸的可靠性

TCP提供一種面向連接的、可靠的字節流服務,
其中,面向連接意味着兩個使用TCP的應用(通常是一個客戶一個服務器)在彼此交換數據之前先見一個一個TCP連接。
在一個TCP連接中,僅有兩方進行彼此通信,字節流服務意味着兩個應用程序通過TCP鏈接交換8bit字節構成的字節流,TCP不在字節流中插入記錄標識符。
對於可靠性,TCP通過以下方式進行保證:

  • **數據包校驗:**目的是檢測數據在傳輸過程中的任何變化,若檢測出包有錯,則丟棄褒文段並且不給出響應,這時TCP發送數據端超時後會重發數據
  • **對失序數據包重新排序:**既然TCP報文段作爲IP數據報來傳輸,而IP數據報的到達可能會失序,因此TCP報文段的到達也可能會失序。TCP將對失序數據進行重排序,然後才交給應用層。
  • **丟棄重複數據:**對於重複數據,能夠丟棄重複數據
  • 應答機制: 當TCP收到發自TCP連接另一端的數據,它將發送一個確認。這個確認不是立即發送,通常將推遲幾分之一秒
  • 超時重發: 當TCP發出一個段後,它啓動一個定時器,等待目的端確認收到這個報文段。如果不能及時收到一個確認,將重發這個報文段
  • 流量控制 TCP連接的每一方都有固定大小的緩衝空間。TCP的接收端只允許另一端發送接收端緩衝區所能接納的數據,這可以防止較快主機致使較慢主機的緩衝區溢出,這就是流量控制。TCP使用的流量控制協議是可變大小的滑動窗口協議。
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章