首先奉上思维导图:
如果你学习计算机网络不想只停留在理论上,希望可以能够达到自己编写一些网络通信程序,那我建议你这么学:
1 学习计算机网络理论知识
你需要掌握基础的如三次握手和四次挥手的过程以及各个状态值,我建议使用 tcpdump 命令实际抓下包就一目了然了,然后就是网络分层,各层的用途,重点熟悉下 TCP/IP 层相关的知识,还有就是 TCP/UDP 的区别,TCP 的滑动窗口机制、拥塞控制算法、TCP 的保序、重传、确认机制。
学习这些知识的时候,一定不要死记硬背,注重理解。我近来面试了一部分学历学校非常好的同学,然而,在问到这块的知识时却大失所望。例如,有的同学只是单纯把三次握手背下来了,我稍微变通一下他就不知道怎么回答了:
1. 如果连接一个目标主机不存在的 IP 地址握手过程是怎样的?连接一个目标 IP 存在但是端口号不存在的主机又是怎样的握手过程呢? 2. A 机器上的进程与 B 机器上的进程进行网络通信,分别经历了哪些网络层。
我整理一些常见的网络面试题,放在这里:
我在知乎上也开过一个 Live 详细讲解了常见的网络面试题:
2 学习Socket 编程
Socket 编程你需要先掌握常用的 Socket API,包括但不局限于:
常用 Berkeley Sockets API 一览表
学习这些 Socket API 的时候,不是让你单纯地记忆这些函数的参数,而是掌握每一个函数的重难点。
例如:
1. 如何将一个 socket 设置成非阻塞模式 2. 阻塞模式下,send 和 recv 函数行为是什么样子的?非阻塞模式下 send/recv 的返回值分别是什么? 3. 客户端发起连接时,如何主动指定通过本地某个端口号去连接?bind 函数如果端口号设置为 0 是什么行为? 4. listen 函数的 backlog 参数用途是什么? 5. 如何实现异步的 connect 函数? 6. accept 函数调用时,三次握手是否已经完成? 7. 如何实现半关闭状态? 8. nagle 算法的用途是什么? 9. select 函数的第一个参数怎么设置?select 函数的超时参数如果设置为 NULL 是什么行为?
接着要重点学习下常用的网络模型:
-
Windows 上常用的网络模型有 select、WSAEventSelect、WSAAsyncSelect、完成端口模型;
-
Linux 上常用的网络模型 select、poll、epoll,epoll 需要重点关注的是水平模式和边缘模式。
当然,也建议一定要理解,不要死记硬背