系统平均负载
判断系统平均负载(Load Average)高不高,不能只看数字本身,关键是看它和CPU核心数的关系,如果是单核,满负载就是1,如果是4核,满负载就是4.
-
黄金法则:平均负载 ≤ CPU核心数,表示系统资源刚好被充分利用,没有进程在排队等待。
-
当平均负载 > CPU核心数时,就意味着有进程在等待CPU,系统可能已经"堵车"了。
这里的"N"代表你服务器的CPU逻辑核心总数:
-
理想状态:负载 ≈ N
每个CPU核心都有任务在跑,资源利用率很高。
-
值得警惕:负载持续 > N * 0.7
系统开始变得繁忙,建议开始调查,防患于未然。
-
需要行动:负载持续 > N * 1.0
系统已经"满负荷",可能出现响应变慢,需要马上排查原因。
-
严重过载:负载 > N * 5.0
系统可能面临严重性能问题,接近"卡死"状态
-
和CPU使用率是两码事 :平均负载高,可能是CPU繁忙,也可能是磁盘I/O(输入/输出)或网络I/O瓶颈导致的进程等待(即进程处于"不可中断睡眠"状态)。比如,磁盘读写很慢时,平均负载会飙升,但CPU使用率可能并不高。
-
先查CPU核心数 :用
nproc或lscpu命令可以快速看到核心数。比如一个4核服务器,只要平均负载持续低于4,都算是正常范围。

top命令

top 的输出分为上下两部分:上方的统计信息区 和下方的进程列表区。
一、统计信息区(前5行)------看整体
这是系统总体情况,重点关注第3行(CPU)和第4、5行(内存)。
1. CPU 状态行(第3行)
这一行通常以 %Cpu(s): 开头,后面跟着一堆百分比。你需要重点关注这几项:
-
us(用户空间) :用户进程(比如你的应用、数据库)消耗的 CPU 占比。这个值越高,说明你的业务程序在真正干活,通常是好事,但如果持续高于 70%-80%,就得留神了。 -
sy(内核空间):操作系统内核消耗的 CPU 占比,比如系统调用、中断等。如果这个值过高(比如超过 20%-30%),可能说明系统调用太频繁,或者有驱动/硬件问题。 -
id(空闲) :CPU 空闲百分比。id越高,系统越闲 。如果id经常接近 0%,说明 CPU 已经满负荷。 -
wa(I/O等待) :CPU 在等待磁盘/网络 I/O 完成的时间。这个值很高(比如超过 10%-20%)而us不高,说明瓶颈在磁盘读写,而不是 CPU 不够快,升级硬盘(比如换 SSD)效果会比加 CPU 更好。 -
st(被偷走) :虚拟机专用。表示宿主机把当前虚拟机的 CPU 分给了其他虚拟机。这个值如果经常超过 5%-10%,说明你买的云服务器"邻居"在抢资源,可能需要升级配置或换机型。
快速判断口诀 :
us 高 + id 低 = 应用忙,正常。
wa 高 + us 低 = 磁盘慢,是瓶颈。
sy 高 = 系统内核开销大,可能有异常。
2. 内存行(第4、5行)
-
第4行(物理内存) :
total(总量)、free(完全空闲)、used(已用)、buff/cache(缓存)。 -
第5行(交换分区) :
total、used、free、avail Mem(可用内存)。
关键认知:Linux 的内存哲学是"闲着也是闲着,不如拿来缓存"
-
不要只看
free很少就觉得内存不够。Linux 会把空闲内存自动拿来当磁盘缓存(buff/cache),以加速读写。当程序需要更多内存时,这部分缓存是可以立即释放的。 -
你应该看的真正指标是第5行最后的
avail Mem(可用内存)。它表示"立即可分给应用程序的内存",这个值如果接近 0,才说明内存真的快用完了。 -
重点关注
swap used。如果交换分区使用量持续增长,说明物理内存真的不够了,系统正在用慢速的硬盘当内存,性能会急剧下降,这是红色警报。
二、进程列表区(任务清单)------看个体
下方列表的每一行代表一个进程,你需要关注这几列:
| 列名 | 含义 | 如何判断 |
|---|---|---|
| PID | 进程ID | 后面可以用于 kill 等操作 |
| USER | 运行用户 | 可识别是系统进程还是应用进程(如 root、mysql) |
| %CPU | 进程占用的CPU百分比 | 注意 :这是"占单个核心"的百分比。比如显示 200%,表示这个进程占满了2个核心。 |
| %MEM | 进程占用的物理内存百分比 | 基于总内存计算,帮助找出"内存大户" |
| RES | 常驻物理内存大小 | 实际占用的物理内存(单位KB/MB) |
| VIRT | 虚拟内存大小 | 申请的总内存,包含未实际分配的,参考价值不大 |
| COMMAND | 进程命令 | 具体是哪个程序 |
查找问题进程的技巧:
-
在
top界面按P键,进程会按 CPU 使用率从高到低排序(找出CPU大户)。 -
按
M键,进程会按内存使用率从高到低排序(找出内存大户)。
三、综合判断思路(实战)
当系统卡顿时,你可以这样组合判断:
-
先看 CPU 行 :如果
us高,去进程列表按P排序列出谁在占用CPU。 -
如果
wa高 ,那问题可能在磁盘,用iostat命令进一步确认。 -
如果内存行里的
avail Mem很小 ,且swap used在增长,去进程列表按M排序,找出吃掉内存最多的进程,考虑是否重启或增加内存。
线程数
线上有个问题,业务高峰时,总发现mq出现一些堆积,想着加大mq的消费线程数,但又怕对cpu和内存造成影响进而影响系统性能。通过分析cpu和内存发现cpu大部分空闲,内存使用也不算很高,于是想着调整线程数,其中负载抖动较高的地方是应用调整消费线程数重启java进程导致的。

看MQ消费逻辑属于哪种类型:
-
CPU密集型 :消息内容需要大量计算(如复杂加密、图像处理、大数据聚合)。这种情况不建议加。4核机器,当前20个线程可能已经产生较多上下文切换开销,再增加反而可能让CPU都在处理线程切换,降低吞吐量。
-
I/O密集型 :消费消息后主要操作是读/写数据库、调用外部API、读写磁盘 。这种情况可以加。因为线程大部分时间在等待I/O响应,CPU空闲,加大线程数能提高并发,让CPU在等待间隙处理更多请求。如果消息消费很快,处理逻辑简单,也可以加大线程数来提升吞吐。
一个常用的估算公式供参考(I/O密集型场景):
最佳线程数 ≈ CPU核心数 / (1 - 阻塞系数)
比如,业务中数据库等待时间约占50%(阻塞系数0.5),那么最佳线程数 ≈ 4 / (1 - 0.5) = 8 个。
-
不要一次性从20调到50 ,风险太大。建议每10-15分钟逐步增加(比如20 → 30 → 40),每个阶段都要监控:
-
CPU使用率是否有突增。
-
业务响应时间(RT)是否变慢。
-
消息积压是否下降。
-
-
当发现吞吐量(TPS)不再随线程数增加而上升,甚至开始下降时,就说明当前线程数已是最优,继续增加只会增加上下文切换开销,这时应回退到上一个稳定值。
容易被忽略的"隐藏"瓶颈
线程数加大后,压力会传导给下游,这些地方的瓶颈可能比你的服务器更先出现:
-
数据库连接池:如果20个线程共用一个连接池(例如连接池最大30),加线程后可能导致连接等待,反而拖慢消费。
-
下游系统:被调用的API能否扛住更大的并发?需要关注下游系统的限流策略。
-
MQ分区(Partition) :如果Kafka/RocketMQ的分区数少于线程数,多出来的线程会空闲,调整线程数也无效。一般建议线程数 ≤ 总分区数。