C#中BigInteger逻辑操作后续循环耗时递增的原因排查
BigInteger操作耗时逐次递增的原因分析
测试代码
用户编写的C#测试程序如下:
using System.Diagnostics; using System.Numerics; using System.Threading; Stopwatch timer = new Stopwatch(); for (int j=0; j<10; j++) { Console.WriteLine("Loop Started {0}",j); timer.Start(); BigInteger bitFields = 0; byte value = 0; for (int i = 0; i < 65400; ++i) { var bb = new BigInteger(value); var result = (bb << (i * 8)); bitFields = bitFields ^ result; } Console.WriteLine("Elapsed duration: {0}", timer.Elapsed.ToString()); timer.Stop(); Console.WriteLine("Loop Completed"); Thread.Sleep(2000); } Console.ReadLine();
问题描述
原本预期每次循环的耗时大致相近,但实际运行时,每次循环的执行时间呈现明显的递增趋势。
原因分析
核心问题出在Stopwatch的使用逻辑上:
Stopwatch.Start()方法的作用是在当前计时的基础上继续累加时间,而非重置计时器从头开始计数。- 第一次循环时,计时器从0开始,记录的是单次循环的耗时;第二次循环调用
Start()时,计时器会从第一次循环结束后的时间点继续计时,输出的是前两次循环的总耗时;第三次则是前三次的总耗时,以此类推,最终表现为耗时逐次递增。
修复方案
在每次循环开始前,使用Restart()方法(等价于先调用Reset()再调用Start()),让计时器每次都从头开始计时:
for (int j=0; j<10; j++) { Console.WriteLine("Loop Started {0}",j); timer.Restart(); // 替换原有的timer.Start() BigInteger bitFields = 0; // 后续代码保持不变 }
额外提示
代码中value变量始终为0,导致bb恒为0,后续的左移和异或操作不会改变bitFields的值(0左移任何位数仍是0,0异或0还是0),这部分逻辑可以根据实际测试需求调整,但不影响计时递增的核心问题。
内容的提问来源于stack exchange,提问作者Azeeb
相关产品推荐
相关产品推荐

