【问题标题】:c#: Will this code get optimized out?c#:这段代码会得到优化吗?
【发布时间】:2010-12-02 17:20:49
【问题描述】:

我在查看第三方外包公司提供给我们的一些代码时遇到了这个小宝石:

try
{
    int i = strOriginalData.IndexOf("\r\n");
    ////System.Diagnostics..EventLog.WriteEntry("i", i.ToString());
}
catch (System.Exception ex)
{
    ////System.Diagnostics..EventLog.WriteEntry("ex", ex.Message);
}

我的问题是编译器会完全优化它吗?当我在 Reflector 中查看编译后的程序集时,它会显示:

try
{
    i = this.strOriginalData.IndexOf("\r\n");
}
catch (Exception exception1)
{
    ex = exception1;
}

i 的声明已移至方法的顶部,并且 Exception 类型的附加声明也在方法的顶部。

所以,由于这段代码实际上并没有做任何事情,我想知道编译器是否足够聪明,可以看到这段代码什么都不做并且可以优化它。

【问题讨论】:

  • 编译器不会对其进行优化,但这类事情可能对性能不利。如果代码本身进入一个异常被抛出然后被吃掉的状态,它将对紧密循环产生剧烈的性能连锁反应。当然是默默地……
  • @chiba:我不认为这是性能问题,更多的是正确性问题。
  • @Henk 我正在考虑以每小时一百万英里的速度循环抛出、捕获然后吞下异常。如果我以前没有多次看到狡猾的“调试”代码这样做,我就不会提及它。
  • @chiba:是的,但这是异常(和)糟糕的代码。我警告说,catch 块通常不利于性能。
  • @Henk 感谢您警告我没有试图传播的神话......不幸的是,我发现上面的代码在新手开发人员中很常见。

标签: c# compiler-optimization


【解决方案1】:

因此,正如您通过 Reflector 发现的那样,C# 编译器 不会对其进行优化。 JIT 编译器 是否会是另一个问题。但是,我猜答案几乎肯定不是。

为什么?因为 JIT 编译器不知道 IndexOf 是一个无聊的方法。换句话说,就 JIT 编译器所知,string.IndexOf 可以定义为

public int IndexOf()
{
   CallAWebService();
}

显然,在这种情况下优化该行会很糟糕。

【讨论】:

    【解决方案2】:

    编译器如何知道IndexOf 没有副作用?

    所以基本上没有,它不会优化它。

    【讨论】:

      【解决方案3】:

      不,它不会被优化。

      另一方面,这是一个非常小的开销。与 string.IndexOf() 设置 catch 块的成本相比,可以忽略不计。

      如果出现异常,则需要付出代价,但这不太可能。

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 2020-03-28
        • 1970-01-01
        • 2013-09-11
        • 1970-01-01
        • 2010-11-02
        • 1970-01-01
        相关资源
        最近更新 更多