下面是正文。
我想起了我刚工作的时候,第一次接触 RPC 协议,当时就很懵,我 HTTP 协议用的好好的,为什么还要用 RPC 协议?
于是就到网上去搜。
不少解释显得非常官方,我相信大家在各种平台上也都看到过,解释了又好像没解释,都在用一个我们不认识的概念去解释另外一个我们不认识的概念,懂的人不需要看,不懂的人看了还是不懂。
这种看了,又好像没看的感觉,云里雾里的很难受,我懂。
为了避免大家有强烈的审丑疲劳,今天我们来尝试重新换个方式讲一讲。
从 TCP 聊起
作为一个程序员,假设我们需要在 A 电脑的进程发一段数据到 B 电脑的进程,我们一般会在代码里使用 socket 进行编程。
这时候,我们可选项一般也就TCP 和 UDP 二选一。TCP 可靠,UDP 不可靠。 除非是马总这种神级程序员(早期 QQ 大量使用 UDP),否则,只要稍微对可靠性有些要求,普通人一般无脑选 TCP 就对了。
类似下面这样。
fd = socket(AF_INET,SOCK_STREAM,0);
其中SOCK_STREAM
,是指使用字节流传输数据,说白了就是TCP 协议。
在定义了 socket 之后,我们就可以愉快的对这个 socket 进行操作,比如用bind()
绑定 IP 端口,用connect()
发起建连。
握手建立连接流程
在连接建立之后,我们就可以使用send()
发送数据,recv()
接收数据。
光这样一个纯裸的 TCP 连接,就可以做到收发数据了,那是不是就够了?
不行,这么用会有问题。
使用纯裸 TCP 会有什么问题
八股文常背,TCP 是有三个特点,面向连接、可靠、基于字节流。
这三个特点真的概括的 非常精辟 ,这个八股文我们没白背。
每个特点展开都能聊一篇文章,而今天我们需要关注的是 基于字节流 这一点。
字节流可以理解为一个双向的通道里流淌的二进制数据,也就是 01 串 。纯裸 TCP 收发的这些 01 串之间是 没有任何边界 的,你根本不知道到哪个地方才算一条完整消息。
正因为这个没有任何边界的特点,所以当我们选择使用 TCP 发送 "夏洛"和"特烦恼" 的时候,接收端收到的就是 "夏洛特烦恼" ,这时候接收端没发区分你是想要表达