Case vs If Else If: Which is more efficient?
Possible Duplicates:
is “else if” faster than “switch() case” ?
What is the relative performance of if/else vs. switch in Java?
我又在运行中编码了……当调试器单步执行case语句时,它会立即跳转到与条件匹配的项,但是当使用if/else指定相同的逻辑时,它会单步执行every if语句,直到找到获胜者。case语句更有效,还是我的调试器只是在优化步骤?(不要担心语法/错误,我把它输入了so,不知道它是否会编译,这是我所追求的原则,我不想把它们作为in t,因为我模糊地记得一些关于case使用带in t的偏移量的情况)我使用c,但我对跨编程语言的一般答案感兴趣。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 | switch(myObject.GetType()){ case typeof(Car): //do something break; case typeof(Bike): //do something break; case typeof(Unicycle): //do something break; case default: break; } |
VS
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 | Type myType = myObject.GetType(); if (myType == typeof(Car)){ //do something } else if (myType == typeof(Bike)){ //do something } else if (myType == typeof(Unicycle)){ //do something } else{ } |
似乎编译器在优化switch语句方面优于if语句。
编译器不知道计算if语句的顺序对您是否重要,并且无法在那里执行任何优化。您可以在if语句中调用方法,从而影响变量。使用switch语句,它知道所有子句都可以同时进行计算,并且可以将它们按最有效的顺序放置。
下面是一个小的比较:http://www.blackwasp.co.uk/speedtestifelswitch.aspx
调试器使其更简单,因为您不想单步执行编译器创建的实际代码。
如果开关包含五个以上的项,则使用查找表或哈希表实现,否则使用if..else实现。
看到密切相关的问题是"else if"快于"switch()case"?.
当然,除了C语言以外的其他语言或多或少也会实现它,但是切换通常更有效。
许多编程语言都对switch语句进行了优化,因此如果结构提供的情况是编译器常量,那么它比标准if else快得多。许多语言使用跳转表或索引分支表来优化switch语句。维基百科对switch语句有很好的讨论。此外,本文还讨论了C语言中的开关优化问题。
需要注意的一点是,switch语句可能会被滥用,根据具体情况,最好使用多态性而不是switch语句。请参阅此处以获取示例。
维基百科的switch语句条目相当大,实际上相当好。有趣的地方:
- 开关本身并不快。它取决于语言、编译器和特定用途。
- 编译器可以使用跳转表或索引函数指针优化开关。
- 这个声明是由斯蒂芬克莱恩(以及其他人)的一些有趣的数学启发而来的。
有关使用C开关进行的奇怪而有趣的优化,请参阅Duff的设备。
它可以对case语句执行此操作,因为值是编译器常量。这里有一个更详细的解释:http://sequence-points.blogspot.com/2007/10/why-is-switch-statement-faster-than-if.html
我相信,因为cases必须是常量值,switch语句实现goto的相等性,因此基于变量的值,它跳到正确的case,而在if/then语句中,它必须计算每个表达式。
我认为这只是使它简单化的调试器。请注意,案例和"if list"最终是不同的。有一个原因可以解释为什么事例块通常以"break"结尾。案例stmt在组装中分解时实际上看起来像这样。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 | if myObject.GetType() == type of Car GOTO START_CAR else if myObject.GetType() == type of Bike GOTO START_BIKE LABEL START_CAR //do something car GOTO END LABEL START_BIKE //do something bike GOTO END LABEL END |
如果你没有休息,那么箱子块会丢失"goto end"stmts,事实上,如果你落在"car"箱子里,你实际上会运行这两个部分。
1 2 3 | //do something car //do something bike GOTO END |