切换外壳还是更快,更好?


71

哪个是更好,最快的方法:if或switch?

if(x==1){
  echo "hi";
} else if (x==2){
  echo "bye";
}

switch(x){
  case 1
    ...
  break;
  default;
} 

31
过早的优化-这两个选项都不会节省任何明显的时间。随您便阅读。
DCoder 2012年

3
由于“开关”没有比较的事实,因此速度稍快。
马尔杜克

1
@Marduk怎么可以切换不比较?

1
@Marduk:您如何看待x1比较?确切地说,它还在内部执行==比较。
ThiefMaster 2012年

1
不要深究代码先生..我不是在问逻辑..我在问哪个更好的方法..如果...或切换..
Ballu Rocks

Answers:


144

您的第一个示例就是错误的。您需要elseif的不仅仅是else

如果使用if..elseif...switch主要是偏好设置。表现是一样的。

然而,如果所有条件的类型x == valuex是相同的在每一个条件,switch通常是有道理的。我也只会switch在有两个以上条件的情况下使用。

其中A的情况下switch,其实是给予你一个性能上的优势是,如果可变部分是一个函数调用:

switch(some_func()) {
    case 1: ... break;
    case 2: ... break;
}

然后some_func()仅在

if(some_func() == 1) {}
elseif(some_func() == 2) {}

它会被调用两次-包括函数调用可能发生的两次副作用。但是,你总是可以使用$res = some_func();,然后用$res你的if条件-这样就可以避免这个问题产品总数。

在那里你的情况不能在所有使用开关是当你有更复杂的条件-switch仅适用于x == yy是一个恒定值。


2
您已经说过,使用elseif或switch主要是优先考虑的问题,并且性能是相同的。我不同意您的看法,对转换语句进行一次评估,然后将结果与每种情况进行比较,如果对elseif进行一次又一次的评估。为此,我认为根据情况的不同之处和方式,一个或另一个条件会更快,更合适。
jortsc 2013年

4
实际上,有一种解决复杂开关情况的方法:<?php $ i = //一个int switch(true){case $ i <0:...; 打破; 情况$ i> = 0:...; 打破; }
SenseException 2014年

In PHP, you can also write 'else if' (in two words) and the behavior would be identical to the one of 'elseif' (in a single word).
一位朋友,

@AFriend尽管(最后我检查了)单个单词的性能稍好一点,elseif因为解释器只需要处理一条指令,而不是两条指令。
安德鲁·丁摩尔

@AndrewDinmore不是我所看到的。仅仅运行了大约20次代码,else if每次都更快。见youself:sandbox.onlinephpfunctions.com/code/...
一个朋友

30

根据phpbench.com,if / elseif稍快一些,尤其是在使用严格比较(===)时。

在此处输入图片说明

但是,如果要在一个可以调用数千次的函数上节省几微秒的时间,那真的很重要。


3
这对答案很有帮助,但是您需要添加更多信息才能使其成为有用的答案。至少链接到phpbench.com该答案的一部分,并直接引用其中的重要部分。我将编辑您的帖子,以向您展示格式正确的答案。
飓风发展

1
尽可能添加来源,并且-更好的是-添加文档的链接和引号。
克里斯蒂安·尤斯(Chris Juth)

17

一般的规则是使用switch时的条件数大于3(为便于阅读)。

if/ else if/else更灵活(因此更好),但switch稍微快一些,因为它只是计算条件一次,然后检查输出,同时if必须做到这一点的每一次。

编辑:似乎switchif毕竟,我可以发誓事实并非如此...


3
基准测试中的嗡嗡声switchif/else仅在两个选项上执行。我知道C#例如switch将使用查找表,并且从5个选择开始更快。我已经执行了与基准测试相同的性能测试,但是有10个选择而不是2选择,而且switch看起来更快!
darkheir 2013年

对于少量比较,是的。但正如Darkheir所提到的,在其他情况下并非如此。
pcarvalho 2014年

4
“*一般规则是使用......” [ [编辑] ](en.wikipedia.org/wiki/Weasel_word)。另请参阅stackoverflow.com/q/7290889/632951
Pacerier,2015年

4

在使用==中,性能if ... elseif相比switch几乎是相同的。但是,使用时===if ... elseif速度大约要快3倍(根据:phpbench)。

通常,switch进行3个以上的比较时,应使用最易读和最易使用的内容。如果性能是主要问题,并且您不需要进行任何类型转换,请if ... elseif与结合使用===


2

这取决于用法。如果您具有fxp状态(在线,离开,dnd,离线...),则最好使用开关。

switch(status)
{
case 'online':
...
}

但是如果你想这样

if ((last_reply.ContainsKey(name)) && (last_reply[name] < little_ago))

要么

if (msg.ToString()[0] == '!')

否则,它会更好地使用。


1

我发现了这篇文章:https : //gist.github.com/Jeff-Russ/2105d1a9e97a099ca1509de1392cd314这表明switch / case比使用===的if / elseif更快。

它们还指示嵌套的if语句,这更有意义,并且可以提供更好的结果。

他们的时代:

嵌套if / elseif ===:0.25623297691345(嵌套IF)

开关/盒:0.33157801628113(SWITCH CASE)

if / elseif ===:0.45587396621704(平IF)

仅当===时:0.45587396621704(仅当)


0

我相信编译器最终会把它们变成非常相似甚至完全相同的代码。

除非您做一些奇怪的事情,否则不要尝试对编译器进行优化。

另外,开发人员的时间通常比运行时(游戏除外)更为重要,因此使其更具可读性和可维护性是更为明智的选择。


0

在我看来,“ if / else”是更快但不比switch好,但是我更喜欢这样:

echo ($x==1?"hi":($x==2?"bye":""));

如果您必须做1,2种情况,如if / else if / else


9
如果观点得到数据和事实的支持,那就很好。
Pacerier'3
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.