关于tcmalloc是否导致std::forward_list排序性能问题的问询
std::forward_list排序性能测试:ptmalloc与tcmalloc的表现差异
测试场景与代码
测试目标为验证std::forward_list的排序性能,流程是先生成1000000个随机数插入容器,重复执行排序操作5次。测试代码如下:
#include <forward_list> #include <chrono> #include <random> #include <iostream> #include <vector> int main() { std::random_device rd; std::mt19937 gen(rd()); std::uniform_int_distribution<int> dis(-100000000, 100000000); std::vector<int> v; for (int i = 0; i < 1000000; ++i) { v.push_back(dis(gen)); } std::forward_list<int> *list; for (int j = 0; j < 5; ++j) { auto list = new std::forward_list<int>(); for (auto it = v.begin(); it != v.end(); ++it) { list->insert_after(list->cbefore_begin(), *it); } auto start = std::chrono::steady_clock::now(); list->sort(); auto end = std::chrono::steady_clock::now(); std::chrono::duration<double> diff = end - start; std::cout << diff.count() << " s\n"; delete list; } }
三组测试结果
- 默认ptmalloc编译(保留delete)
编译命令:g++ test2.cpp -o test2 -O2
输出:
0.994629 s 3.01309 s 2.98853 s 2.99701 s 3.01637 s
- tcmalloc编译(保留delete)
编译命令:g++ test2.cpp /usr/local/lib/libtcmalloc_minimal.a -o test2 -O2
输出:
0.551351 s 0.550282 s 0.590626 s 0.613431 s 0.559123 s
- ptmalloc编译(删除delete语句)
输出:
0.893076 s 0.952251 s 0.95971 s 0.931195 s 0.922877 s
结果分析与结论
你的怀疑完全相反——tcmalloc不仅没有引发性能问题,反而在该场景下表现出显著的性能优势,核心原因在于两者内存管理机制的差异:
ptmalloc的性能波动原因:每次循环执行
delete list后,ptmalloc回收的内存块易产生碎片,导致后续new的forward_list节点在内存中分布零散。而std::forward_list的排序依赖节点内存访问的连续性,内存碎片会大幅降低CPU缓存命中率,使得排序时间从第一次的1s飙升到后续的3s。当去掉delete后,内存无需回收,新分配的节点能保持更优的内存布局,缓存命中率稳定,排序时间也维持在~0.9s左右。tcmalloc的性能优势:tcmalloc针对小内存块的分配/回收做了专项优化,即使频繁执行
delete和new,也能高效复用内存,避免严重的碎片问题。这使得每次排序时,节点的内存布局都能保持缓存友好,因此排序时间稳定在0.55-0.61s,远优于ptmalloc的表现。
简言之,这个测试中tcmalloc是性能提升的关键因素,而非问题所在;ptmalloc的内存碎片问题才是导致后续排序性能骤降的根源。
内容的提问来源于stack exchange,提问作者szh
相关产品推荐
相关产品推荐

