粘包问题(TCP面向字节流批量发送数据导致)

粘包问题出现的原因

        由于TCP协议网络传输数据的基本单位是字节流,所以当应用程序收到了传输的数据时,看到的是一连串的字节数据,而TCP协议网络传输数据有滑动窗口的机制(核心就是批量传输数据,推荐看TCP中窗口和滑动窗口的含义以及流量控制),所以传输过来的数据可能是多个数据包,因此就不知道从哪个部分到哪个部分是一个完整的应用层数据包

如何避免粘包问题

        避免粘包问题的核心就是明确两个包之间的边界

        1.对于定长的包,保证每次都按固定大小读取即可

        2.对于变长的包,可以在包头的位置,约定一个包总长度的字段,从而就知道了包的结束位置

例子:约定包的前两个字段表示包总长度(程序员规定的),这样约定后,应用程序在获得数据时就会先读取包头的两个字段,读取到包总长度后再根据包总长度准确读取当前数据包的所有数据

        后面再重复上述操作即可

        3.对于变长的包,可以在包和包之间添加明确的分隔符(应用层协议,程序猿自己来定的,只有保证分隔符不和正文冲突就行)

粘包问题的一些注意点

        1.首先要明确,粘包问题中的“包”是应用层的数据包

        2.在TCP的协议头中,没有如同UDP一样的”报文长度“这样的字段(有一个首部长度的字段表示的只是TCP报头的长度),但有一个”序号“字段

        3.站在传输层的角度,TCP是一个一个报文过来的,按照序号排好序放在缓冲区中

        4.站在应用层的角度,看到的只是一连串的字节数据

对于UDP来说是否存在粘包问题呢

        UDP是不存在粘包问题的

        1.对于UDP,如果上层还没有交付数据,UDP的报文长度依然存在,同时,UDP是一个一个把数据交付给应用层,就有很明确的数据边界

        2.站在应用层的角度,使用UDP时,要么收到完整的UDP报文,要么不收,不会出现”半个的情况“

你可能感兴趣的:(tcp/ip,网络,服务器)