C++ 计算机网络 常考面试题总结

1. 简述 TCP 滑动窗口以及重传机制

滑动窗口机制

TCP滑动窗口是流量控制的核心机制,基于发送窗口和接收窗口实现:

  1. 核心原理:接收方通过报文首部的窗口大小字段,告知发送方自己的接收缓冲区剩余空间,发送方以此控制发送数据量,避免接收方缓冲区溢出;
  2. 窗口分类:发送窗口:分为已发送未确认、未发送但可发送、超出窗口不可发送三部分,窗口随ACK确认报文向右滑动;接收窗口:仅接收窗口内的数据,超出部分丢弃或暂存,接收后向发送方回传ACK并滑动窗口。

重传机制

TCP通过超时重传和快速重传解决数据丢失问题:

  1. 超时重传:发送方为每个报文段设置定时器,超时未收到ACK则重传该报文段,超时时间随网络状况动态调整(RTO算法);
  2. 快速重传:接收方收到失序报文段时,立即发送重复ACK(针对已收到的最后一个有序报文段),发送方收到3个重复ACK,无需等待超时,直接重传丢失的报文段。

2. 滑动窗口过小怎么办?

滑动窗口过小会导致发送方发送数据量受限,大幅降低传输效率,核心解决方式分为接收方优化和发送方优化:

  1. 接收方优化:及时清理接收缓冲区,释放空间后立即通过ACK报文更新窗口大小,避免窗口长期处于极小值;
  2. 发送方优化:启用窗口扩大因子(TCP选项),将窗口大小字段的有效范围从16位扩展到32位,支持更大的窗口尺寸;
  3. 协议层面:配合慢启动和拥塞避免算法,在网络拥塞解除后,逐步增大拥塞窗口,间接提升实际发送窗口的可用大小。

3. 三次握手时每次握手信息没收到,分情况介绍

TCP三次握手的核心是建立可靠连接,每次握手报文丢失的处理逻辑不同,核心如下:

第一次握手(客户端发SYN)丢失

  • 现象:服务器未收到SYN,不会响应;客户端未收到ACK,触发超时重传;
  • 处理:客户端按超时时间重传SYN报文,重传次数达到上限则建立连接失败,终止流程。

第二次握手(服务器发SYN+ACK)丢失

  • 现象:客户端未收到SYN+ACK,超时重传SYN;服务器未收到客户端的ACK,认为连接未建立,超时后释放半连接资源;
  • 处理:客户端重传SYN,服务器收到后重新发送SYN+ACK;若多次重传仍无响应,双方均终止连接建立。

第三次握手(客户端发ACK)丢失

  • 现象:服务器未收到ACK,处于SYN_RECV半连接状态,超时后重传SYN+ACK;客户端已进入ESTABLISHED状态,认为连接已建立;
  • 处理:服务器重传SYN+ACK,客户端收到后再次发送ACK;若服务器重传次数耗尽,释放半连接;此时若客户端向服务器发数据,服务器会因未建立连接发送RST报文,客户端终止连接。

4. 简述 TCP 的 TIME_WAIT,为什么需要有这个状态?

TIME_WAIT 状态定义

TIME_WAIT是TCP连接关闭的主动关闭方(通常是客户端)进入的状态,处于该状态的连接会持续2MSL时间,之后才完全关闭。

核心作用

  1. 保证最后的ACK报文到达服务器:主动关闭方发送的最后一个ACK可能丢失,服务器会重传FIN报文,主动关闭方在TIME_WAIT状态下可接收并重传ACK,避免服务器因未收到ACK一直处于CLOSE_WAIT状态;
  2. 避免旧连接的报文干扰新连接:网络中可能存在延迟的旧连接报文,TIME_WAIT等待2MSL(报文最大生存时间),确保旧报文完全从网络中消失,防止其被新的同端口连接接收,造成数据混乱。

5. 简述什么是 MSL,为什么客户端连接要等待 2MSL 的时间才能完全关闭?

MSL 定义

MSL(Maximum Segment Lifetime,报文最大生存时间)是TCP报文在网络中的最大存活时间,超过该时间的报文会被路由器丢弃,Linux下默认MSL为30秒。

等待 2MSL 的原因

  1. 保证双向报文均失效:主动关闭方等待1个MSL,确保自己发送的最后一个ACK报文到达服务器;再等待1个MSL,确保服务器重传的FIN报文(若ACK丢失)到达自己,同时让网络中所有旧连接的报文完全失效;
  2. 避免连接复用冲突:TIME_WAIT结束后,端口才能被重新使用,2MSL的等待时间确保新连接不会接收到旧连接的延迟报文,保证连接的可靠性。

6. 说说什么是 SYN flood,如何防止这类攻击?

SYN flood 定义

SYN flood是一种DDOS攻击,攻击者向服务器发送大量伪造的SYN报文,使服务器处于SYN_RECV半连接状态,耗尽服务器的半连接队列资源,导致合法客户端无法建立连接。

防护措施

  1. 增大半连接队列:调整内核参数(如Linux的tcp_max_syn_backlog),扩大半连接队列容量,提升抗攻击能力;
  2. 启用SYN Cookie:服务器不存储半连接信息,而是通过SYN报文的参数生成Cookie,在第三次握手时验证Cookie有效性,避免半连接队列耗尽;
  3. 限流与过滤:通过防火墙、CDN对异常IP进行限流,过滤伪造的SYN报文;
  4. 缩短半连接超时时间:减少服务器在SYN_RECV状态的停留时间,快速释放无效半连接资源。

7. 说说什么是 TCP 粘包和拆包?

核心定义

TCP是面向字节流的协议,无消息边界,粘包和拆包是数据传输中因底层机制导致的报文合并/拆分现象:

  • 粘包:发送方连续发送的多个小报文,被内核合并成一个报文发送,接收方一次性收到多个报文的数据;
  • 拆包:发送方发送的大数据报文,超过MSS(最大报文段长度)或TCP缓冲区大小,被内核拆分成多个报文发送,接收方分多次接收。

产生原因

  1. 粘包:发送方Nagle算法合并小报文、接收方接收缓冲区未及时读取数据;
  2. 拆包:报文超过MSS、发送方缓冲区不足、网络MTU限制。

解决方法

在应用层定义消息边界,如固定长度、分隔符、消息头+消息体(含长度字段)。

8. 说说 TCP 与 UDP 在网络协议中的哪一层,他们之间有什么区别?

协议层级

TCP和UDP均属于传输层协议,基于网络层的IP协议提供端到端的通信服务。

核心区别

9. 说说从系统层面上,UDP 如何保证尽量可靠?

UDP本身不提供可靠性保障,需在系统层和应用层结合优化,实现“尽量可靠”:

  1. 系统层优化:增大UDP发送缓冲区和接收缓冲区,避免因缓冲区溢出导致数据丢失;启用网卡多队列、大页内存,提升UDP数据包的处理效率,减少内核态到用户态的拷贝开销;避免UDP分片,控制数据包大小不超过MTU(1500字节),防止分片丢失导致整个报文失效。
  2. 应用层适配:实现序列号和ACK确认机制,对丢失的报文进行重传;加入校验和校验数据完整性,丢弃损坏的报文;采用超时重传和滑动窗口机制,控制发送速率,避免网络拥塞。

10. 说一说 TCP 的 keepalive,以及和 HTTP 的 keepalive 的区别?

TCP keepalive

TCP keepalive是传输层的保活机制,用于检测TCP连接是否存活:

  1. 核心逻辑:连接空闲超过指定时间(默认2小时),发送方发送keepalive探测报文,接收方正常则回复ACK,异常则判断连接断开;
  2. 作用:检测对端是否异常下线(如断电、崩溃),及时释放无效连接资源。

HTTP keepalive

HTTP keepalive是应用层的长连接机制,也叫持久连接:

  1. 核心逻辑:HTTP/1.1默认启用,通过Connection: keep-alive头部,让TCP连接在多次请求-响应后保持打开,避免频繁建立/关闭TCP连接;
  2. 作用:减少TCP三次握手、四次挥手的开销,提升HTTP请求的传输效率。

核心区别

11. 简述 TCP 协议的延迟 ACK 和累计应答

延迟 ACK(Delayed ACK)

  1. 定义:接收方收到TCP报文后,不立即发送ACK,而是延迟一段时间(通常200ms)再发送,是TCP的优化机制;
  2. 作用:将ACK与后续的发送数据报文合并(捎带应答),减少网络报文数量,降低开销;
  3. 注意:延迟时间有上限,避免发送方超时重传,若期间收到新的有序报文,会立即发送累计ACK。

累计应答(Cumulative ACK)

  1. 定义:TCP的ACK是累计确认,ACK报文的确认号表示接收方已正确收到确认号之前的所有字节;
  2. 作用:简化ACK机制,无需对每个报文段单独确认,减少ACK报文数量;
  3. 场景:接收方收到失序报文段时,仅确认已收到的最后一个有序字节,触发发送方的快速重传机制。

12. 说说 TCP 如何加速一个大文件的传输?

TCP传输大文件的加速核心是提升吞吐量、减少传输延迟,从协议机制、系统优化、应用层适配三方面入手:

  1. 协议机制优化:增大滑动窗口:启用窗口扩大因子,提升发送窗口和接收窗口大小,让发送方一次发送更多数据;调整拥塞控制算法:使用CUBIC、BBR等高性能拥塞控制算法,快速提升拥塞窗口,避免网络拥塞时的吞吐量骤降;关闭Nagle算法:减少小报文合并的延迟,提升大文件传输的连续性。
  2. 系统层优化:增大TCP发送/接收缓冲区大小,避免缓冲区溢出导致的数据丢失;启用零拷贝(如sendfile),减少数据在用户态与内核态之间的拷贝开销;提升网卡MTU,减少IP分片,提升传输效率。
  3. 应用层适配:分块传输大文件,结合多线程/多连接并行传输(如HTTP Range请求);启用数据压缩,减小文件体积,降低传输数据量。

13. 服务器怎么判断客户端断开了连接?

服务器判断客户端断开连接,分为主动断开和异常断开两种情况,核心方式如下:

  1. 检测FIN/RST报文:客户端主动断开时,会发送FIN报文,服务器收到后,向客户端发送ACK,进入CLOSE_WAIT状态,确认客户端正常断开;客户端异常断开(如强制杀死进程),服务器后续向客户端发送数据时,会收到RST报文,直接判断连接断开。
  2. TCP keepalive 探测:启用TCP keepalive机制,服务器向空闲的客户端发送探测报文,若多次未收到ACK,判定客户端异常断开,释放连接资源。
  3. 应用层心跳机制:在应用层实现心跳包(如定时发送空请求/特定指令),客户端定时向服务器发送心跳,服务器若超时未收到心跳,判定客户端断开连接。

14. 说说浏览器从输入 URL 到展现页面的全过程

整个过程分为7个核心步骤,覆盖应用层、传输层、网络层、数据链路层,直至页面渲染:

  1. URL解析:浏览器解析URL,提取协议(如HTTP/HTTPS)、域名(如www.baidu.com)、端口(默认80/443)、路径(如/index.html);
  2. DNS解析:浏览器通过DNS协议将域名解析为IP地址,依次查询浏览器缓存、本地DNS缓存、路由器缓存、根域名服务器、顶级域名服务器、权威域名服务器;
  3. TCP连接建立:基于解析的IP和端口,客户端与服务器进行TCP三次握手,建立可靠连接(HTTPS需额外进行TLS握手,完成加密协商);
  4. HTTP请求发送:浏览器构造HTTP请求报文(请求行、请求头、请求体),通过TCP连接发送给服务器;
  5. 服务器处理并响应:服务器接收请求,解析请求内容,处理业务逻辑(如查询数据库、读取文件),构造HTTP响应报文(状态行、响应头、响应体),发送给浏览器;
  6. TCP连接关闭:若为短连接,请求响应完成后进行TCP四次挥手关闭连接;若为长连接,连接保持供后续请求使用;
  7. 页面渲染:浏览器接收响应数据,解析HTML构建DOM树,解析CSS构建CSSOM树,结合二者生成渲染树,再进行布局、绘制,最终展现完整页面。

15. 简述TCP的拥塞控制机制(慢启动、拥塞避免、快速恢复)

TCP拥塞控制核心通过拥塞窗口(cwnd) 调控发送速率,分为三个核心阶段,配合快速恢复机制处理丢包:

  1. 慢启动:连接建立初期,cwnd从1开始,每经过一个RTT就翻倍,直到cwnd达到慢启动阈值(ssthresh),避免初始阶段大量数据注入导致网络拥塞。
  2. 拥塞避免:达到ssthresh后,cwnd每次RTT仅增加1,缓慢提升发送速率,平衡吞吐量与网络承载能力。
  3. 快速恢复:收到3个重复ACK时,不触发慢启动,而是将cwnd减半并进入拥塞避免阶段,同时重传丢失的报文段,避免吞吐量骤降。

16. 简述TCP的快速重传与快速恢复的协同工作原理

  1. 快速重传:接收方收到失序报文时,立即发送重复ACK,发送方收到3个重复ACK后,判定对应报文丢失,立即重传,无需等待超时。
  2. 快速恢复:重传后将cwnd设置为ssthresh = cwnd / 2,并进入拥塞避免阶段,而非慢启动,保证高吞吐量场景下的传输稳定性。

17. 说说TCP的保活机制(keepalive)的实现细节

  1. 触发条件:连接空闲时间达到tcp_keepalive_time(默认2小时),内核发送第一个保活探测报文。
  2. 探测流程:若对端正常回复ACK,重置空闲时间;若连续探测(默认9次) 无响应,判定连接断开。
  3. 核心特点:属于传输层机制,仅检测连接存活,不传递业务数据;需与应用层心跳配合,才能检测应用层异常。

18. 简述UDP的封装与解包过程(结合网络分层)

  1. 封装:应用层数据 → UDP首部(源端口、目的端口、长度、校验和) → 网络层IP首部(源IP、目的IP、协议号(17)) → 数据链路层帧头帧尾。
  2. 解包:数据链路层剥帧头帧尾 → 网络层剥IP首部 → 传输层剥UDP首部,提取应用层数据。
  3. 关键注意:UDP无拥塞控制,解包时需校验校验和,丢弃损坏报文。

19. 说说如何在系统层面优化UDP的传输可靠性

  1. 应用层确认:给每个UDP报文加序列号+时间戳,接收方校验序列号,丢失则重传请求。
  2. 缓冲区优化:增大UDP接收缓冲区,避免因瞬时高并发导致报文丢失。
  3. 限速与兜底:对异常高频IP限流,避免恶意请求耗尽UDP传输资源。

20. 简述TCP的拥塞窗口与滑动窗口的区别

21. 说说SYN攻击的原理与防护(结合SYN flood)

  1. 原理:攻击者发送大量伪造SYN报文,占满服务器半连接队列(SYN_RECV),导致合法连接无法建立。
  2. 防护:启用SYN Cookie(不存储半连接信息,通过报文参数生成校验值)、增大半连接队列、开启TCP同步校验。

22. 简述HTTP的长连接与短连接的区别

  1. 短连接:每次请求建立TCP连接,响应后断开,开销大,适合低频请求。
  2. 长连接:HTTP/1.1默认,复用TCP连接处理多次请求,减少三次握手开销,是高并发服务的基础。

23. 说说TCP的紧急指针(URG)的作用

  1. 核心功能:标记报文中的紧急数据,接收方需优先处理紧急数据,再处理普通数据。
  2. 场景:若客户端发送“紧急停止”指令,可通过URG快速触发服务端中断当前任务。

24. 简述TLS握手的核心步骤

  1. 客户端Hello:发送支持的加密套件、随机数。
  2. 服务端Hello:选择加密套件、发送随机数、证书。
  3. 密钥交换:客户端验证证书,生成预主密钥,用服务端公钥加密后发送。
  4. 握手完成:双方生成会话密钥,后续数据通过对称加密传输。

25. 说说如何处理TCP粘包问题

  1. 定长包:固定每个请求的报文长度,不足补0。
  2. 分隔符:用特定字符(如\r\n)作为报文边界。
  3. 头部长度字段:报文头加“数据长度”,接收方按长度截取,是最常用的方法。

26. 服务器如何处理大量TIME_WAIT连接

  1. 核心原因:主动关闭方未等待2MSL,导致端口耗尽。
  2. 解决:启用tcp_tw_reuse(复用TIME_WAIT端口)、缩短tcp_fin_timeout、增大端口范围。

27. 简述IP分片的原理与重组

  1. 原理:IP报文超过MTU时,被切分为多个分片,每个分片含标识、片偏移、MF标志。
  2. 重组:接收方按标识重组,所有分片到达后,按片偏移拼接为完整报文。

28. 说说select、poll、epoll的核心区别

29. 如何区分“网络断开”与“服务崩溃”

  1. 网络断开:recv返回0,send触发SIGPIPE,无RST报文。
  2. 服务崩溃:recv收到RST报文,连接直接断开,服务器无任何响应。

30. 说说TCP连接的异常检测优先级

  1. 第一优先级:RST报文(服务崩溃、端口未监听)。
  2. 第二优先级:超时(网络拥塞、任务执行超时)。
  3. 第三优先级:乱序/重复报文(网络抖动、重传机制异常)。

31. 说说UDP在通信中的应用限制

  1. 无连接:无法保证报文到达,需应用层加序列号+ACK。
  2. 缓冲区限制:接收缓冲区需设置上限,避免恶意请求耗尽内存。

32. 简述TCP的半关闭(half-close)的作用

  1. 核心场景:客户端发送“结束请求”后,关闭写端,仅保留读端,等待服务器响应完毕。
  2. 作用:避免误发数据,确保服务器完成所有响应后再关闭连接。

33. 说说如何做TCP连接的健康检查

  1. 传输层:发送空报文,检测ACK是否正常。
  2. 应用层:发送“心跳包”,检查服务是否正常处理请求。
  3. 联动:若健康检查失败,自动切换到备用节点。

34. 简述DNS解析在跨地域部署中的作用

  1. 核心作用:将域名解析为就近的节点IP,减少网络延迟。
  2. 故障场景:错误解析到非就近节点,导致响应慢,需启用智能DNS。

35. 如何处理TCP的异常断开

  1. 检测:recv返回-1,errno为ECONNRESET,判定为异常断开。
  2. 处理:清理该连接的上下文,释放端口资源,尝试重连。

36. 说说网络字节序与主机字节序的转换

  1. 核心函数:htons(主机→网络)、ntohs(网络→主机)。
  2. 场景:跨节点通信时,必须转换端口/序列号,避免协议解析错误。

37. 说说TCP连接的优雅关闭

  1. 四步挥手:主动方发FIN,被动方回ACK+FIN,主动方回ACK。
  2. 优雅点:关闭前执行清理逻辑,释放资源,避免数据异常。

38. 说说UDP报文丢失的排查方法

  1. 抓包:tcpdump -i eth0 udp port 端口 -w udp.pcap。
  2. 校验:对比发送方序列号与接收方,丢失则重传。
  3. 兜底:报文丢失触发重传请求,保证数据完整。

39. 简述TLS在网络服务中的作用

  1. 加密:保护通信数据,防止被篡改。
  2. 认证:验证服务端证书,确保连接的是合法节点。

40. 说说如何做TCP的流量控制

  1. 传输层:滑动窗口机制,接收方通过rwnd告知发送方最大发送量。
  2. 应用层:设置限流策略,控制并发数,避免服务过载。
C++ 常考面试题总结 文章被收录于专栏

本专栏系统梳理C++方向, 大中厂高频高频面试考点 , 内容皆来自真实面试经历,从基础语法、内存管理、STL与设计模式,到操作系统与项目实战,结合真实面试题深度解析,帮助开发者高效查漏补缺,提升技术理解与面试通过率,打造扎实的C++工程能力.

全部评论
有没有一整套的链接
点赞 回复 分享
发布于 昨天 22:18 湖北
比我之前看的面试题精简多了 里面很多之前我面试的时候面试官也问到过的 之前我看的那一大堆面试题 我看了一周都没记住 东西太多了
点赞 回复 分享
发布于 昨天 22:13 黑龙江
有点难啊
点赞 回复 分享
发布于 昨天 21:26 广东

相关推荐

昨天 15:27
已编辑
广东药科大学 后端工程师
一面: 70 分钟1.实习的专项的项目规模、成员规模2.Redis 性能 QPS 有多高?为什么要用本地缓存3.同一 APP 网关下、查询业务流量过大会否影响网关、是否做了资源隔离,带宽 / 连接数占满是否会导致网关扛不住?4.容灾怎么扩容5.介绍一下 Redis 的哈希表扩容6.假如说你来设计一个哈希表、它如果这个负载因子过高要扩容的话、你会怎么扩容?7.它为什么要进行这个渐进式?这个哈希扩容的过程、它这个有什么作用?8.Redis Zset 的使用场景和作用9.跳表的查询、插入操作的时间复杂度是多少?10.像我们经常用的这种数据结构、假如说红黑树它其实也是 Ologn、那跳表跟这个红黑树这种结构比、它也两个都是 Ologn 跳表有什么优势?11.八股:AOP、Java 的 volatile 关键字、Java 的 ThreadLocal12.如何实现统计 Web 项目过去 10 分钟每个 API 的访问次数、并在看板展示前 10/100 名 API 访问量的需求?13.如何从生产者、消息队列本身、消费者三个阶段保证消息队列不丢消息?14.手撕:二叉树的层序遍历15.是否使用过双端队列(前后可 push、pop)?如何在双端队列基础上设计支持按下标随机访问的队列?能否详细介绍环形切片的实现方式?二面:四十分钟手撕:统计公平数对的数目√/*给你一个下标从 0 开始、长度为 n 的整数数组 nums 、和两个整数 lower 和 upper 、返回 公平数对的数目 。如果 (i, j) 数对满足以下情况、则认为它是一个 公平数对 :• 0 <= i < j < n,且*/问了一些实习就没了主要是因为这家面试的一面二面的面试体验很好、面试官会引导还会问一些自己的过往经历和生活、介绍业务也很详细面试体验无敌好大家可以面一下看看
查看16道真题和解析
点赞 评论 收藏
分享
评论
5
3
分享

创作者周榜

更多
牛客网
牛客网在线编程
牛客网题解
牛客企业服务