直接回答:标准姿势:testing.B 驱动,b.N 由框架自动调准到每次运行约 1 秒(-benchtime 控制);用 -benchmem 拿分配指标;结果必须跑多次(-count=10)用 benchstat 做统计显著性判定;被测函数的结果要赋给包级变量(sink)防止编译器把整个计算优化掉。
展开解析:测不准的常见原因按坑位排序:编译器优化——常量折叠(参数是字面量直接算完)、死代码消除(结果没人用整个函数消失)、内联改变测量对象,对策是 sink 变量与 runtime.KeepAlive;环境噪声—— turbo boost 频率漂移、同机其他负载、笔记本省电模式,对策是固定机器、跑多轮取分布、b. 环境一致性比绝对值重要;b.N 内部状态——setup 放循环外(b.ResetTimer 之前),计时中做初始化数据全废;分配干扰——测试本身分配触发 GC,-benchmem 分离看 allocs/op,必要时 b.ReportAllocs;微基准外推谬误——单函数快 30% 不等于接口快 30%(Amdahl),微基准只做候选方案筛选,结论以系统级 profile 验证。进阶工具:benchstat 的 p-value 与 delta 判断“快了 5%”是不是噪声;-cpu=1,2,4 看并行扩展性;fuzz 式随机输入防 benchmark 数据过于规整(分支预测全中)。发布规范:贴 goos/goarch/CPU 型号、Go 版本、benchstat 输出——可复现是性能声明的底线。
追问方向:为什么 b.RunParallel 的吞吐测试易高估?timer 重置还有哪些场景?
(约 470 字)