面经-C语言——堆和栈的区别,引用和指针区别,Linux的常用指令,RS232和RS485,TCP连接建立与断开
- 堆(Heap)和栈(Stack)的详细比较
- 引用和指针区别对比表:
- Linux的常用指令
- RS232和RS485的详细比较:
- TCP连接建立与断开
- 三次握手(建立连接)详解
- 第一次握手:客户端发起连接
- 第二次握手:服务器响应
- 第三次握手:客户端确认
- 四次挥手(断开连接)详解
- 第一次挥手:客户端发起断开
- 第二次挥手:服务器确认
- 第三次挥手:服务器发起断开
- 第四次挥手:客户端最终确认
- 重要概念和意义
-
堆(Heap)和栈(Stack)的详细比较
对比维度 | 堆(Heap) | 栈(Stack) |
---|
基本定义 | 动态分配的内存空间,用于存储复杂的数据结构 | 一种遵循后进先出(LIFO)原则的线性数据结构 |
内存分配方式 | 动态分配,大小可以随程序运行时改变 | 静态分配,大小在编译时确定,malloc,free,或者new,delete |
访问速度 | 相对较慢,使用复杂的数据结构管理 | 非常快,由编译器管理 |
内存管理 | 需要手动管理(在C/C++中) | 系统自动管理,随着函数调用自动分配和回收 |
存储的数据类型 | 复杂的数据结构,如对象、大型数据 | 局部变量、函数调用信息、基本数据类型 |
生命周期 | 可以在整个程序运行期间存在 ,手动释放 | 随着函数调用的结束而立即释放 |
内存分配效率 | 相对较低 | 非常高 |
空间大小 | 通常更大,可以在运行时动态调整,取决于内存大小 | 空间有限,编译时确定 |
溢出风险 | 堆溢出(不释放会产生内存泄漏) | 栈溢出(递归调用过深) |
使用场景 | 动态分配大小的数据、复杂数据结构 | 函数调用、局部变量、临时存储 |
内存碎片 | 容易产生内存碎片 | 几乎不会产生内存碎片 |
线程特性 | 通常是进程或线程共享的 | 每个线程有独立的栈 |
引用和指针区别对比表:
特征 | 引用 (Reference) | 指针 (Pointer) |
---|
定义 | 变量的别名,必须在声明时初始化 | 存储内存地址的变量 |
空值 | 不能为空 | 可以为空 (nullptr) |
重新赋值 | 初始化后不能更改引用的对象 | 可以更改指向的对象 |
内存操作 | 不需要显式内存管理 | 需要手动管理内存 |
语法 | 使用 & 符号声明 | 使用 * 符号声明 |
间接访问 | 直接访问对象 | 需要解引用才能访问对象 |
常见使用 | 函数参数传递、避免复制 | 动态内存分配、数据结构 |
示例 | int x = 10; int& ref = x; | int* ptr = new int(10); |
Linux的常用指令
命令 | 英文全称 | 功能 | 示例 |
---|
ls | List | 列出目录内容 | ls -l (长格式显示目录内容) |
cd | Change Directory | 切换目录 | cd /home (进入"/home"目录) |
pwd | Print Working Directory | 显示当前工作目录路径 | pwd (直接显示当前路径) |
mkdir | Make Directory | 创建新目录 | mkdir mydir (创建"mydir"目录) |
rm | Remove | 删除文件或目录 | rm myfile.txt (删除"myfile.txt"文件) |
cp | Copy | 复制文件或目录 | cp file1.txt file2.txt (复制文件) |
mv | Move | 移动或重命名文件/目录 | mv file1.txt newdir (移动文件) |
touch | Touch | 创建空文件或更新时间戳 | touch file.txt (创建新文件) |
cat | Concatenate | 查看文件内容 | cat file.txt (显示文件内容) |
grep | Global Regular Expression Print | 文件内容查找 | grep "pattern" file.txt (查找匹配行) |
chmod | Change Mode | 修改文件/目录权限 | chmod +x script.sh (设置可执行) |
chown | Change Owner | 修改文件/目录所有者 | chown user1 file.txt (更改所有者) |
man | Manual | 查看命令手册 | man ls (查看ls命令帮助) |
ps | Process Status | 查看进程状态 | ps -ef (显示所有进程) |
top | Table of Processes | 实时显示系统资源 | top (显示系统进程和资源) |
RS232和RS485的详细比较:
对比项目 | RS232 | RS485 |
---|
传输距离 | 短距离,通常<15米 | 长距离,最大可达1200米 |
通信模式 | 点对点 | 多点总线网络 |
最大节点数 | 2个设备 | 最多32个设备 |
传输速率 | 低速,最高约20Kbps | 高速,可达10Mbps |
抗干扰能力 | 较弱 | 非常强 |
信号类型 | 单端信号 | 差分信号 |
电气特性 | ±5V到±15V | 差分电压±1.5V到±5V |
常见应用 | 调制解调器、串口通信 | 工业控制、自动化系统 |
线缆要求 | 普通串行通信电缆 | 屏蔽双绞线 |
成本 | 较低 | 相对较高 |
通过这个表格还是可以很轻松地发现其联系的,因为其采用屏蔽双绞线,所以是差分信号,所以成本较高,抗干扰能力很强,速度很高,传输距离远。
TCP连接建立与断开
阶段 | 三次握手(建立连接) | 四次挥手(断开连接) |
---|
第一步 | 客户端发送SYN报文 | 客户端发送FIN报文 |
目的 | 发起连接请求 | 表示数据传输结束 |
标志位 | SYN | FIN |
第二步 | 服务器回复SYN+ACK报文 | 服务器回复ACK报文 |
目的 | 确认客户端连接请求 | 确认客户端断开请求 |
标志位 | SYN、ACK | ACK |
第三步 | 客户端发送ACK报文 | 服务器发送FIN报文 |
目的 | 确认服务器响应,连接建立 | 服务器准备断开连接 |
标志位 | ACK | FIN |
第四步 | - | 客户端发送ACK报文 |
目的 | - | 确认服务器断开,连接关闭 |
标志位 | - | ACK |
关键特点 | 同步序列号,确认通信能力 | 确保数据传输完整,优雅关闭 |
三次握手(建立连接)详解
第一次握手:客户端发起连接
- 客户端向服务器发送连接请求报文段
- 报文中包含SYN(同步)标志位
- 选择一个初始序列号(Sequence Number)
- 标志着开始建立TCP连接
第二次握手:服务器响应
- 服务器接收到客户端的连接请求
- 服务器发送确认报文段
- 报文中包含SYN和ACK标志位
- 确认客户端的序列号
- 服务器也选择自己的初始序列号
第三次握手:客户端确认
- 客户端接收到服务器的确认报文
- 发送最后一个确认报文
- 包含ACK标志位
- 确认服务器的序列号
- 连接正式建立
四次挥手(断开连接)详解
第一次挥手:客户端发起断开
- 客户端数据发送完毕
- 发送FIN(Finish)报文段
- 表示客户端不再发送数据
- 进入FIN_WAIT_1状态
第二次挥手:服务器确认
- 服务器接收到FIN报文
- 发送ACK确认报文
- 表示同意断开连接请求
- 客户端进入FIN_WAIT_2状态
第三次挥手:服务器发起断开
- 服务器完成数据发送
- 发送FIN报文段
- 表示服务器准备关闭连接
第四次挥手:客户端最终确认
- 客户端接收服务器FIN报文
- 发送ACK确认报文
- 连接完全关闭
- 双方正式断开TCP连接
重要概念和意义
为什么需要三次握手
为什么需要四次挥手
- 保证数据传输完整
- 确保双方都有机会完成数据发送
- 优雅地终止连接