5

如果我有一个包含大量 if else 语句的方法,例如:

public void myMethod()
{
    if(..)
    else if(..)
    else if(...)
    else if(...)
    else if(...)

    //and so on            
}

将 return 放在这些语句中会更快,以便在发现一个语句为真后不检查其余代码,还是让编译器命中结束括号会更快?

我想这归结为一个问题:return 语句是否有效?

编辑:问题的重点:假设您有一个不断运行的游戏循环,其代码包含很多方法和“else ifs”。如果我必须每秒更新 2000 个不同的对象 60 次,那就是每秒检查 120000 个“else ifs”(至少)。因此,随着时间的推移,这个问题的答案可能会产生影响。

4

3 回答 3

18

没关系。
任何理智或疯狂的编译器都会为任一选项生成相同的字节码。(假设你写的代码实际上是等价的)

您应该使用更具可读性的方法。

于 2013-04-16T00:35:37.857 回答
12

SLaks 的回答当然是正确的。但我认为你提出这个问题的事实表明你对 if-else 的含义有误解。当你说

if(x) X();
else if(y) Y();
else if(z) Z();
return;

这意味着与

if(x)
{
  X();
}
else
{
  if (y)
  {
    Y();
  }
  else
  {
    if (z)
    {
      Z();
    }
  }
}
return;

如果,比如说,分支x被选中,那么y永远不会被检查;控制直接跳到return后面X()

事实上,在 C# 中没有“else if”之类的东西——或者 C、C++、Java 或 JavaScript。只有“其他”;如果您碰巧在if之后发表声明else,那是您的事。没有比这更多的“如果”

if (x) X();
else while(y) Y();

是一个“else while”语句。else您可以在;之后放置您想要的任何语句 大多数人选择放一个if或一个块语句,但你可以放任何你喜欢的语句。(*)

更新:

我知道 else if 'skips',问题的关键是添加一个 return 让它直接跳出来,而不是花时间首先跳过它们。例如,在极端情况下,连续一百万个 if else 语句。它仍然需要找到行尾(这可能需要时间)。我对吗?

好的,我们需要去一个更低的层次。if-else语句编译如下:

if (condition) 
    Consequence() 
else 
    Alternative();
Continuation();

实际上是转化为一系列 goto 语句:

if (!condition) 
    goto ALTERNATIVE;
Consequence();
goto CONTINUATION;
ALTERNATIVE:  Alternative();
CONTINUATION: Continuation();

所以如果你有

if (x) X(); 
else if (y) Y();
else if (z) Z();
return;

首先变成

if (x)
    X(); 
else 
{
    if (y)
        Y();
    else
    {
        if (z)
            Z();
    }
}

然后变成

if (!x) goto XALTERNATIVE;
X(); 
goto CONTINUATION;
XALTERNATIVE: if (!y) goto YALTERNATIVE;
Y();
goto CONTINUATION;
YALTERNATIVE: if (!z) goto CONTINUATION;
Z();
CONTINUATION: return;

这是否回答你的问题?


(*) 本地声明除外;C# 禁止这样做。

于 2013-04-16T02:50:53.260 回答
0

当用作条件的保护时它是有效的,但在你的情况下它并不重要,因为一旦执行这些语句中的一个,其他语句就不会被验证,但是如果你正在做这样的事情:

if(...){return;}
if(...){return;}
if(...){return;}
if(...){return;}
if(...){return;}

那么这很重要。

于 2013-04-16T00:40:46.107 回答