我只是试图确定每个“if”语句对我的C#应用程序在具有大量迭代的循环中使用时的性能的影响。我还没有找到关于这个的主题,所以我创建了这个。
对于测试我做了2个循环:一个没有“if”,一个有一个“if”语句。代码如下。
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Diagnostics;
namespace IfPerformance
{
class Program
{
static void Main(string[] args)
{
int N = 500000000;
Stopwatch sw = new Stopwatch();
double a = 0, b = 0;
bool f;
sw.Restart();
for (int i = 0; i < N; i++)
{
a += 1.1;
f = a < N;
}
sw.Stop();
Console.WriteLine("Without if: " + sw.ElapsedMilliseconds + " ms");
a = 0;
sw.Restart();
for (int i = 0; i < N; i++)
{
if (a < N)
a += 1.1;
else
b += 1.1;
}
sw.Stop();
Console.WriteLine("With if: " + sw.ElapsedMilliseconds + " ms");
Console.ReadKey();
}
}
}
我使用“Optimize code”构建选项和“Start without debugging”运行测试。结果如下: 没有if:154 ms 使用if:742 ms
这意味着单个“if”语句会使性能降低近5倍。我认为这将有所帮助。
另外,我注意到在一个大循环中存在几个额外的“if”可能会使我的最终应用程序减慢25%,这在我看来很重要。
具体而言,我正在对一组数据运行蒙特卡罗优化,这需要在整个数据集中进行多次循环。循环包含分支,这取决于用户设置。从这一点开始“如果”出现。
我对专业人士的表现方面的问题是:
如果我的方向错误,请发表您的意见。
答案 0 :(得分:13)
没关系...... 你正在测试5亿次迭代......而且只需不到一秒......最糟糕的情况......
正如评论所说,开始时你会遇到麻烦,因为你不会在调试中运行以测试性能,即便如此,你还要考虑其他很多东西需要考虑(这是关于性能测试的一个大世界,它并不像通常那样简单。)
现在,请注意你在两个地方做了两件不同的事情。如果你想看到if的性能,你应该让它们基本相同。我确信分支会改变IL代码开始......
最后,但并非最不重要,正如我再次说的那样......它确实很重要......除非你真的需要运行5亿次,并且在很多地方都有这个,以至于你的程序开始变慢因为这一点。
如果你可以在if语句中保存一些微秒,那么可以阅读。
请Eric Lippert阅读这些文章(谁只有“250K代表,而且i̶s̶是C#编译团队的主要开发人员:)谁会让你正确的方向:
(谈到这一点,我猜想垃圾收集(第4条)可能需要考虑......)
然后看看:this elaborate answer about the topic
最后,但并非最不重要的是,看看Writing Faster Managed Code: Know What Things Cost。这是来自Microsoft CLR Performance Team的Jan Gray。我会诚实地说我没有读过这个但是 :)。不过,我会稍后......
它继续......:)
答案 1 :(得分:2)
这些代码示例是两个不同的代码,一个是布尔赋值,另一个是条件语句,因此这不是评估性能的合适方法
答案 2 :(得分:1)
那些基准测试基本上没有告诉你什么。 除了额外的if之外,还有更多的东西在起作用。 您还必须考虑分支预测和缓存。 这种微观优化只会阻碍你编写好的代码。 您将花费更多时间来优化无用的东西,而不是花时间在软件中实现好的功能......
以这种方式思考,如果您的代码中只有一个设计错误,那么任何优化都不会对您有所帮助。 例如,使用不合适的数据结构(例如,“快速”查找而不是字典的列表)。