为什么C++中for循环执行前后无法测出时间差?
C++循环与函数计时问题解答
问题背景
用户尝试计算C++中迭代函数与递归函数的时间差,最初无法测出for循环执行耗时,具体测试过程如下:
第一次测试
测试代码
int main (){ //int arr[7] = {1,2,3,4,5,6,7}; ll arr[100000]; unsigned __int64 one = std::chrono::duration_cast<std::chrono::milliseconds>(std::chrono::system_clock::now().time_since_epoch()).count(); for (ll i = 0; i < 100000; i++) { arr[i]=i+1; } unsigned __int64 two = std::chrono::duration_cast<std::chrono::milliseconds>(std::chrono::system_clock::now().time_since_epoch()).count(); // int a=binSearchRecursive(arr,6755,0,10000); // int b=binSearchIter(arr,6755,0,10000); // unsigned __int64 three = std::chrono::duration_cast<std::chrono::milliseconds>(std::chrono::system_clock::now().time_since_epoch()).count(); cout << "Recursive :"<< one << " " <<two <<endl; cout << "Iterative :" <<two-one << std :: endl; // cout <<a<<" " << b ; return 0; }
运行结果
Recursive :1635504404011 1635504404011 Recursive :0
第二次测试
修改点:新增第二个for循环替换数组已有值,将计时精度从毫秒改为纳秒
测试代码
int main (){ //int arr[7] = {1,2,3,4,5,6,7}; ll arr[100000]; unsigned __int64 one = std::chrono::duration_cast<std::chrono::nanoseconds>(std::chrono::system_clock::now().time_since_epoch()).count(); for (ll i = 0; i < 100000; i++) { arr[i]=i*3; } for (long long i = 0; i < 100000; i++) { arr[i]=arr[i]*arr[i+1]; } unsigned __int64 two = std::chrono::duration_cast<std::chrono::nanoseconds>(std::chrono::system_clock::now().time_since_epoch()).count(); // int a=binSearchRecursive(arr,6755,0,10000); // int b=binSearchIter(arr,6755,0,10000); // unsigned __int64 three = std::chrono::duration_cast<std::chrono::milliseconds>(std::chrono::system_clock::now().time_since_epoch()).count(); //cout << "Recursive :"<< one << " " <<two <<endl; cout << "Recursive :"<< two-one <<endl; //int b = arr[23423] + arr[73432]; //cout << "Iterative :" << three- two << std :: endl; // cout <<a<<" " << b ; return 0; }
疑问
运行后得到差值为1029000,该差值是两个for循环的总耗时还是仅第一个for循环的耗时?
问题解答
第一次测试差值为0的原因
- 10万次数组赋值操作本身执行耗时远小于1毫秒,毫秒级精度不足以测出差异
- 若开启了编译器优化(如O2、O3等级),编译器会识别到arr数组后续没有被使用,会直接删除无副作用的for循环代码,导致两次计时中间没有有效执行逻辑,差值自然为0
第二次测试差值的含义
你代码中one时间戳取在两个for循环执行前,two时间戳取在两个for循环全部执行完成后,因此1029000纳秒的差值是两个for循环的总耗时,换算后约为1.03毫秒,符合两次10万次循环的执行耗时水平。
计时优化建议
- 关闭编译器优化,或在计时结束后主动使用数组中的值(比如输出数组某随机下标的值),避免无副作用的代码被优化删除
- 短耗时计时优先使用
std::chrono::steady_clock而非std::chrono::system_clock,前者为单调时钟,不会因为系统时间同步出现跳变,计时准确性更高 - 可以将被测代码重复执行多次(如1000次)后统计总耗时,平均得到的单次耗时误差更小
内容的提问来源于stack exchange,提问作者Spartex
相关产品推荐
相关产品推荐

