传输层的两大协议是TCP 和 UDP ,他们在传输数据的时候起到了不可替代的作用。那么什么是TCP呢?
首先TCP是一个网络传输协议,这个协议保证了可靠的数据传输。TCP是面向字节流的,全双工的(也就是通信双方互相发消息)。往往应用于对实时性要求没那么高的场景,但是又要要求把数据完全传输过去(不是确保100%能传过去,传不过去就超时重传)。
Socket clientSocket = serverSocket.accept();
InputStream inputStream = clientSocket.getInputStream();
OutputStream outputStream = clientSocket.getOutputStream();
相反UDP是保证的不可靠的传输,面向数据报的,但是UDP可以保证实时性,UDP说:实在不行就丢包呗,反正我把大部分数据准时传到就行。因此在我们所看的抖音直播,王者荣耀,吃鸡,这些实时性要求比较高的app中应用的主要是UDP协议,你们有没有感觉一整直播就卡了,然后那段主播说了啥咱也不知道。王者遇到过这种情况吧,走不动,走到界外去了,吃鸡的时候你还没开枪就被秒了。最直观的例子,老师上网课,上着上着发现老师没画面了。
总结来说UDP协议适用于需要快速传输实时数据的场景,它具有较低的延迟和较小的传输开销。由于UDP不提供确认和重传机制,它能够更快地传输数据,但也可能导致数据的丢失或乱序。
但是今天的主角是TCP,上面的例子就是要理解一下TCP和UDP的区别
如图所示就是TCP报文段的结构:
(1)首先就是作为传输层协议,必须知道端口号是啥。源端口和目的端口各占2B,表示发送方和接收方使用的端口号。
(2)序号:占4B TCP连接中传送的字节流中每个字节都要按照顺序编号。比如说一个报文段的序号字段值是301,而携带的数据共有100B,表明本报文段的数据的最后一个字节号是400,下一个报文段的数据序号要从401开始。有这个序号就像我们都有名字是一个道理,如果涉及到两个数据重复传输的时候,这个序号就起到了至关重要的作用。
(3)确认号,也要占4B,若确认号为N,则表示前N-1个数据都收到了。
(4)这里的数据偏移其实指的是首部长度,占4位。指的是TCP报文段的数据起始处距离TCP报文段的起始处有多远,因为有选项这个东西,因此可以说,如果选项完全没有,TCP报头长度是20个字节。4个比特位最多能表示15,而首部的长度是4个字节(一个字节表示四个比特位),因此我们得出结论,首部最大的长度是60,如果去掉20个固定的,剩下的选项部分最多占40个字节。因此首部长度是20-60个字节,
(5)保留位:占6位,保留以后使用,万一以后有一天TCP需要扩展一些新的功能,就可以使用这个保留位来表示了。
TCP的机制
(1)确认应答机制:对于TCP协议来说,要解决一个很重要的问题,那就是可靠传输,可靠传输并不能保证100%把数据发送到对方手里,但是会尽可能给发送方知道接收方是否接受到消息。下图就是一个应答机制。
在网络通信中,会出现后发先至现象,如果不加控制,有时候会很容易误解发送方的意思。
因此就有了解决方法:
-
序列号与确认机制:TCP协议通过使用序列号和确认机制来确保数据的有序传输。接收方会按照序列号的顺序重新组装数据包,并发送确认消息给发送方,告知已经收到的数据包序列号,从而保证数据的有序性。
确认序号的特点:连续递增,确认序号就是应答数据的最后一个字节的序号+1
比如说接收序号是1-1000,此处应答报文的确认序号是1001.也可以理解成小于1001的数据都确认收到了。
确认位 ACK=1时,我们说确认号字段有效,当ACK=0时,确认号无效。
总结一下TCP的确认应答机制有保证TCP最核心的功能的作用,即可靠传输。而为什么TCP可靠传输也不一定能保证百分百传输到位呢?举例来说:每个交换机/路由器的转发能力存在着上限,这取决于芯片硬件设备的能力!一旦某个设备需要转发的数据量超出了自身的极限,那么多出来的部分就会被直接丢弃掉。
(2)超时重传机制:如果接收方没有收到任何数据,也一定不会给任何的应答!,此时,发送饭就可以根据是否收到了ACK来区分是否丢包。
发送方发送出数据之后,如果正常收到ACK也一定需要一些时间的,发送方也会进行一定时间的等待,但是一旦等待时间超过了某个阈值,就可以认为是丢包了!如果说数据传输晚了,也一并视为传输失败!发现丢包就要重传!下图表示了超时重传。
如果说接收方重传的时候接收到了数据,但是丢失的数据一起传过来了,会导致重复传输,这里就会根据TCP所携带的序号来进行去重。
除此之外,有一个接收缓冲区,在这里可以针对收到的数据进行排序。也是针对后发先至进行的一个调整。因为我们希望消息还是按照顺序到达对方手里的。而超时重传也不是无限等待的,如果说,网络出现严重的故障,重传了若干次还是不成功,那么就进行重置连接,也就是RST,当RST=1时,表示TCP连接中出现了严重的差错(如主机崩溃)必须释放连接,然后重新的建立传输连接。