点运营商在运营方面的成本是多少?

时间:2015-10-14 06:13:28

标签: c# asp.net optimization

我有一个像

这样的循环
for (int i = 2; i <= ViewBag.numPages; ++i)

我想知道如果我把它写成

会更快
for (int i = 2, n = ViewBag.numPages; i <= n; ++i)

如果可能,请给我一个深层次(低级别)的解释

2 个答案:

答案 0 :(得分:1)

  

点运算符在运算方面是否有任何成本?

这取决于。对于您的ASP.NET代码:

for (int i = 2; i <= ViewBag.numPages; ++i)

...然后上面的内容可能会受到优化(或者可能是CPU缓存),因此您在尝试优化时所做的任何事情都可能不明显。

COM

但是,您的问题标题未提及ASP.NET(虽然后来标记为),因此想象一下ViewBag实际上是 COM对象< /强>

for (int i = 2; i <= ViewBag.numPages; ++i)

...那将是非常昂贵的,不受.NET优化的影响我不会想到。调用COM,特别是通过IDispatch调用COM比访问本地对象上的.NET属性要慢得多。

所以在COM的情况下你应该:

for (int i = 2, n = ViewBag.numPages; i <= n; ++i)

答案 1 :(得分:1)

假设ViewBag.numPages在循环期间保持不变,我赞成第二种变体,即:

for (int i = 2, n = ViewBag.numPages; i <= n; ++i)

为什么?

  • 也许你的第一个numPages是一个简单的字段,但如果它是一个非平凡的属性,你的循环必须在每次迭代之前评估它(调用它的getter),这肯定比评估它更昂贵它一次然后缓存结果。

  • 编译器优化是编译器的一个实现细节,你不知道编译器为了提高性能到底做了什么。

    手动缓存ViewBag.numPages意味着您不必依赖编译器可能会或可能不会为您执行的优化。

话虽如此,如果ViewBag.numPages是一个(常量)字段,而不是属性,那么两个代码变体的执行速度可能都非常接近(在最好的情况下,我们正在谈论差异在访问CPU寄存器与原子地访问可能在CPU内存缓存中的一个内存位置之间,差异并不重要。