¿Es "else if" más rápido que "switch() case"? [duplicar]


Posible Duplicado:
¿Hay alguna diferencia significativa entre usar if / else y switch-case en C#?

Soy un ex Pascal, actualmente aprendiendo C#. Mi pregunta es la siguiente:

¿Es el siguiente código más rápido que hacer un cambio?

int a = 5;

if (a == 1)
{
    ....
}
else if(a == 2)
{
    ....
}
else if(a == 3)
{
    ....
}
else if(a == 4)
{
    ....
}
else
    ....

Y el interruptor:

int a = 5;

switch(a)
{
    case 1:
        ...
        break;

    case 2:
        ...
        break;

    case 3:
        ...
        break;

    case 4:
        ...
        break;

    default:
        ...
        break;


}

¿Cuál es más rápido?

Estoy preguntando, porque mi programa tiene una estructura similar (muchas, muchas sentencias "else if"). Debo convertirlos en los interruptores?

Author: Community, 2009-04-20

14 answers

Para unos pocos elementos, la diferencia es pequeña. Si usted tiene muchos elementos que sin duda debe utilizar un interruptor.

Si un conmutador contiene más de cinco elementos, se implementa utilizando una tabla de búsqueda o una lista de hash. Esto significa que todos los elementos obtienen el mismo tiempo de acceso, en comparación con una lista de if:s donde el último elemento tarda mucho más tiempo en llegar, ya que primero tiene que evaluar todas las condiciones anteriores.

 509
Author: Guffa,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2009-04-20 11:14:15

¿por Qué te importa?

El 99.99% de las veces, no debería importarte.

Es poco probable que este tipo de micro-optimizaciones afecten el rendimiento de su código.

Además, si necesita atención, entonces debería estar haciendo perfiles de rendimiento en su código. En cuyo caso sería trivial averiguar la diferencia de rendimiento entre una caja de conmutación y un bloque if-else.

Edit: Para mayor claridad: implementa cualquier diseño que sea más claro y más fácil de mantener. En general, cuando se enfrentan a un gran interruptor-caso o si-else bloquear la solución es utilizar polimorfismo. Encontrar el comportamiento que está cambiando y encapsular. He tenido que lidiar con un enorme y feo código de caso de cambio como este antes y generalmente no es tan difícil de simplificar. Pero oh, tan satisfactorio.

 151
Author: Wedge,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2009-04-20 19:20:11

Creyendo esta evaluación de rendimiento, el caso del interruptor es más rápido.

Esta es la conclusión:

Los resultados muestran que la instrucción switch es más rápida de ejecutar que la escalera if-else-if. Esto se debe a la capacidad del compilador para optimizar la instrucción switch. En el caso de la escalera if-else-if, el código debe procesar cada instrucción if en el orden determinado por el programador. Sin embargo, debido a que cada caso dentro de una instrucción switch no se basa en en casos anteriores, el compilador puede reordenar las pruebas de tal manera que proporcione la ejecución más rápida.

 26
Author: Michael Klement,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2009-04-20 11:11:19

Otra cosa a considerar: ¿es realmente este el cuello de botella de su aplicación? Hay casos extremadamente raros en los que realmente se requiere una optimización de este tipo. La mayoría de las veces puede obtener mejores aceleraciones repensando sus algoritmos y estructuras de datos.

 13
Author: Vilx-,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2009-04-20 11:18:41

Yo diría que el interruptor es el camino a seguir, es a la vez más rápido y mejor práctica.

Hay varios enlaces como ( http://www.blackwasp.co.uk/SpeedTestIfElseSwitch.aspx ) que muestran pruebas de referencia que comparan los dos.

 8
Author: Shaun Bohannon,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2009-04-20 11:10:56

No debería ser difícil de probar, crear una función que cambia o ifelse entre 5 números, lanzar un rand(1,5) en esa función y loop que un par de veces mientras que el tiempo.

 6
Author: Ólafur Waage,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2009-04-20 11:10:07

Switch es generalmente más rápido que una larga lista de ifs porque el compilador puede generar una tabla de salto. Cuanto más larga sea la lista, mejor será una sentencia switch sobre una serie de sentencias if.

 6
Author: Steven,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2009-04-20 11:11:16

Mucho más importantes que los beneficios de rendimiento de switch (que son relativamente leves, pero vale la pena señalar) son los problemas de legibilidad.

Por mi parte, encuentro una sentencia switch extremadamente clara en intent y espacios en blanco puros, en comparación con las cadenas de ifs.

 5
Author: annakata,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2009-04-20 11:24:33

No estoy seguro, pero creo que la velocidad de uno u otro cambia dependiendo del lenguaje de programación que esté utilizando.

Normalmente prefiero usar switch. De esta manera el código es fácil de leer.

 5
Author: user308693,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2010-04-04 12:47:32

Técnicamente, producen exactamente el mismo resultado por lo que deberían ser optimizables de la misma manera. Sin embargo, hay más posibilidades de que el compilador optimice el caso de cambio con una tabla de salto que el ifs.

Estoy hablando del caso general aquí. Para 5 entradas, el número medio de pruebas realizadas para el ifs debe ser inferior a 2,5, suponiendo que ordene las condiciones por frecuencia. Apenas un cuello de botella para escribir a casa a menos que en un bucle muy apretado.

 4
Author: jfclavette,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2009-04-20 11:10:52

switch normalmente se traduce en una tabla de búsqueda por el compilador, si es posible. Así que la búsqueda de un caso arbitrario es O (1), en lugar de hacer algunas comparaciones de casos antes de encontrar el que desea.

Así que en muchos casos if/else if la cadena será más lenta. Sin embargo, dependiendo de la frecuencia con la que sus casos están siendo afectados, eso puede no hacer ninguna diferencia.

 4
Author: Joey,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2009-04-20 11:13:27

Respuesta corta: La instrucción Switch es más rápida

La sentencia if necesita dos comparaciones (cuando ejecuta su código de ejemplo) en promedio para llegar a la cláusula correcta.

La instrucción switch el número promedio de comparaciones será uno independientemente de cuántos casos diferentes tenga. El compilador / VM habrá hecho una "tabla de búsqueda" de posibles opciones en tiempo de compilación.

Las máquinas virtuales pueden optimizar la instrucción if de manera similar si ejecuta este código a menudo?

 3
Author: AnnaR,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2009-04-20 11:21:12

Dado que la declaración switch expresa la misma intención que su if / else pero de una manera más restringida y formal, su primera suposición debería ser que el compilador será capaz de optimizarlo mejor, ya que puede sacar más conclusiones sobre las condiciones colocadas en su código (es decir, solo un estado puede ser verdadero, el valor que se compara es un tipo primitivo, etc.).) Esta es una verdad general bastante segura cuando se comparan dos estructuras de lenguaje similares para el tiempo de ejecución rendimiento.

 2
Author: mquander,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2009-04-20 19:25:51

Véase http://msdn.microsoft.com/en-us/library/system.reflection.emit.opcodes.switch%28VS.71%29.aspx

Instrucción Switch básicamente una tabla de búsqueda tiene opciones que se conocen y si la instrucción es como tipo booleano. de acuerdo a mí interruptor y si-else son iguales, pero para el interruptor de la lógica puede ayudar más mejor. mientras que si-else ayuda a entender en la lectura también.

 2
Author: User42590,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2012-09-29 08:24:12