Apollo 技术文档Apollo 技术文档
指南
  • 架构概述
  • BigWorld 架构深度解析
  • BigWorld 进程架构与玩家生命周期
  • AOI九宫格系统详解
  • AOI广播与消息去重
  • Base 模块
  • Core 模块
  • Runtime 模块
  • Data 模块
  • Network 模块
  • /modules/actor.html
  • Game 模块
  • BigWorld 模块
服务器应用
API 参考
QA
GitHub
指南
  • 架构概述
  • BigWorld 架构深度解析
  • BigWorld 进程架构与玩家生命周期
  • AOI九宫格系统详解
  • AOI广播与消息去重
  • Base 模块
  • Core 模块
  • Runtime 模块
  • Data 模块
  • Network 模块
  • /modules/actor.html
  • Game 模块
  • BigWorld 模块
服务器应用
API 参考
QA
GitHub
  • MMORPG 架构 QA

Q67: 如何进行热点代码优化?

核心结论

热点代码优化的核心,不是“把每一行都写快”,而是把真正吃时间的少数路径找出来,确认瓶颈类型,再用最合适的手段去改。

更务实的顺序通常是:

  • 找热点
  • 判断热点类型
  • 改最影响用户体验和系统上限的部分
  • 用数据验证收益

如果没有证据链,所谓热点优化很容易变成局部微调。

一、先确认什么才算热点

热点通常不是“代码看起来复杂”,而是:

  • 占总 CPU 时间高
  • 调用频率极高
  • 尾延迟影响明显
  • 在高峰场景下被反复放大

所以热点可能是:

  • 一个大函数
  • 一段小循环
  • 一把高争用锁
  • 一次重复序列化

二、先分清热点属于哪一类

常见可以分成:

  • 纯计算热点
  • 内存访问热点
  • 锁竞争热点
  • I/O 或系统调用热点
  • 无效工作热点

这一步非常关键,因为不同类型的热点解法完全不同。

例如:

  • 纯计算可能适合算法优化或 SIMD
  • 内存访问问题更可能要改数据布局
  • 锁热点则要减少共享

三、先砍无效工作量,通常收益最高

很多热点并不是“必要工作太慢”,而是“做了太多不必要的事”。

常见例子包括:

  • 重复计算
  • 无效广播
  • 重复序列化
  • 不必要的格式化和日志

减少工作量,往往比把同样工作做得更快更有效。

四、局部优化要服从整体链路

一段函数即使优化了 30%,如果它不在关键链路上,整体收益可能很小。

所以热点优化应该结合:

  • 调用路径
  • 业务场景
  • 高峰流量下的放大效应

这也是为什么 flame graph、tracing 和业务指标要一起看。

五、常见优化方向

1. 算法和数据结构

如果复杂度本身不对,其他微优化都很有限。

2. 数据布局

减少 cache miss、减少指针追逐,经常比改几条指令更值。

3. 批量处理

很多高频小操作合并后收益很明显。

4. 降低锁竞争

把串行点拆掉,往往比单线程路径抠极致更有效。

5. 减少分配和拷贝

这在消息、事件、同步链路里很常见。

六、优化后一定要重新验证

一个完整的热点优化至少应该验证:

  • CPU 占比有没有下降
  • 尾延迟有没有改善
  • 是否引入了新瓶颈
  • 是否破坏了可维护性

没有回归验证,优化结论通常不可靠。

七、工程上更稳妥的优化顺序

常见顺序是:

  1. 用 profiling 锁定热点
  2. 判断是算法、布局、锁还是 I/O 问题
  3. 优先减少无效工作
  4. 再做局部深挖

这通常比一上来就手改汇编或硬抠细节更稳。

八、常见误区

1. 热点优化就是把函数写得更短

不对。瓶颈可能根本不在函数代码量,而在访问模式或并发结构。

2. 看到热点函数就立刻内联、展开循环

这可能有用,也可能只是噪音。先确认瓶颈类型更重要。

3. 微优化积累起来一定有大收益

如果方向不对,积累的只是维护成本。

参考资料

  • flame graph、热点分析和性能回归实践资料
在 GitHub 上编辑此页
最后更新: 3/20/26, 6:06 AM
贡献者: cuihairu