Instrucción switch
(C++)
Permite la selección entre varias secciones de código, dependiendo del valor de una expresión entera.
Sintaxis
selection-statement
:
switch
(
init-statement
optC++17condition
)
statement
init-statement
:
expression-statement
simple-declaration
condition
:
expression
attribute-specifier-seq
optdecl-specifier-seq
declarator
brace-or-equal-initializer
labeled-statement
:
case
constant-expression
:
statement
default
:
statement
Comentarios
Una instrucción switch
hace que el control se transfiera a una instrucción labeled-statement
en el cuerpo de la instrucción, en función del valor de condition
.
condition
debe tener un tipo entero o ser de un tipo de clase que tiene una conversión no ambigua a un tipo entero. La promoción integral tiene lugar como se describe en Conversiones estándar.
El cuerpo de la instrucción switch
consta de una serie de etiquetas case
y una etiqueta optional default
. labeled-statement
es una de estas etiquetas y las instrucciones que siguen. Las instrucciones con etiquetas no son requisitos sintácticos, pero la instrucción switch
no tiene sentido sin ellas. No puede haber dos valores constant-expression
en las instrucciones case
que se evalúen en el mismo valor. La etiqueta default
puede aparecer solo una vez. La instrucción default
se coloca a menudo al final, pero puede aparecer en cualquier parte del cuerpo de la instrucción switch
. Una etiqueta case
o default
solo puede aparecer en una instrucción switch
.
El elemento constant-expression
de cada etiqueta case
se convierte en un valor constante que tiene el mismo tipo que condition
. Después, se compara con condition
para ver si son iguales. El control pasa a la primera instrucción después del valor constant-expression
de case
que coincida con el valor de condition
. El comportamiento resultante se muestra en la siguiente tabla.
Comportamiento de la instrucción switch
Condición | Acción |
---|---|
El valor convertido coincide con el de la expresión de control promovida. | El control se transfiere a la instrucción que sigue a esa etiqueta. |
Ninguna de las constantes coincide con las constantes de las etiquetas case ; hay una etiqueta default . |
El control se transfiere a la etiqueta default . |
Ninguna de las constantes coincide con las constantes de las etiquetas case ; no hay una etiqueta default . |
El control se transfiere a la instrucción situada detrás de la instrucción switch . |
Si se encuentra una expresión coincidente, la ejecución puede continuar por etiquetas case
o default
posteriores. La instrucción break
se usa para detener la ejecución y transferir el control a la instrucción situada detrás de la instrucción switch
. Sin una instrucción break
, se ejecutan todas las instrucciones que hay desde la etiqueta case
coincidente hasta el final de la instrucción switch
, incluida la etiqueta default
. Por ejemplo:
// switch_statement1.cpp
#include <stdio.h>
int main() {
const char *buffer = "Any character stream";
int uppercase_A, lowercase_a, other;
char c;
uppercase_A = lowercase_a = other = 0;
while ( c = *buffer++ ) // Walks buffer until NULL
{
switch ( c )
{
case 'A':
uppercase_A++;
break;
case 'a':
lowercase_a++;
break;
default:
other++;
}
}
printf_s( "\nUppercase A: %d\nLowercase a: %d\nTotal: %d\n",
uppercase_A, lowercase_a, (uppercase_A + lowercase_a + other) );
}
En el ejemplo anterior, uppercase_A
se incrementa si c
es una mayúsculacase'A'
. La instrucción break
detrás de uppercase_A++
finaliza la ejecución del cuerpo de la instrucción switch
y el control pasa al bucle while
. Sin la instrucción break
, la ejecución pasaría a la siguiente instrucción con etiqueta, de modo que lowercase_a
y other
también se incrementarían. La instrucción break
para case 'a'
tiene un propósito similar. Si c
es una minúscula case'a'
, lowercase_a
se incrementa y la break
instrucción finaliza switch
el cuerpo de la instrucción. Si c
no es 'a'
ni 'A'
, se ejecuta la instrucción default
.
Visual Studio 2017 y versiones posteriores (disponible en el modo /std:c++17
y versiones posteriores): el atributo [[fallthrough]]
se especifica en el estándar de C++17. Puede usarse en una instrucción switch
. Es una sugerencia para el compilador (o para cualquier persona que lea el código) de que el comportamiento de paso explícito es intencionado. Actualmente, el compilador de Microsoft C++ no advierte sobre el comportamiento de paso explícito, por lo que este atributo no tiene ningún efecto sobre el comportamiento del compilador. En el ejemplo, el atributo se aplica a una instrucción vacía dentro de la instrucción etiquetada sin terminar. En otras palabras, el punto y coma es necesario.
int main()
{
int n = 5;
switch (n)
{
case 1:
a();
break;
case 2:
b();
d();
[[fallthrough]]; // I meant to do this!
case 3:
c();
break;
default:
d();
break;
}
return 0;
}
Visual Studio 2017, versión 15.3 y posteriores (disponible en el modo /std:c++17
y posteriores): una instrucción switch
puede tener una cláusula init-statement
, que termina con un punto y coma. Introduce e inicializa una variable cuyo ámbito está limitado al bloque de la instrucción switch
:
switch (Gadget gadget(args); auto s = gadget.get_status())
{
case status::good:
gadget.zip();
break;
case status::bad:
throw BadGadget();
};
Un bloque interno de una instrucción switch
puede contener definiciones con inicializadores siempre que sean accesibles, es decir, siempre que las rutas de ejecución posibles no las omitan. Los nombres proporcionados mediante estas declaraciones tienen ámbito local. Por ejemplo:
// switch_statement2.cpp
// C2360 expected
#include <iostream>
using namespace std;
int main(int argc, char *argv[])
{
switch( tolower( *argv[1] ) )
{
// Error. Unreachable declaration.
char szChEntered[] = "Character entered was: ";
case 'a' :
{
// Declaration of szChEntered OK. Local scope.
char szChEntered[] = "Character entered was: ";
cout << szChEntered << "a\n";
}
break;
case 'b' :
// Value of szChEntered undefined.
cout << szChEntered << "b\n";
break;
default:
// Value of szChEntered undefined.
cout << szChEntered << "neither a nor b\n";
break;
}
}
Una instrucción switch
puede estar anidada. Cuando está anidada, las etiquetas case
o default
se asocian con la instrucción switch
más cercana que las contenga.
Comportamiento específico de Microsoft
Microsoft C++ no limita el número de valores case
de una instrucción switch
. El número solo está limitado por la memoria disponible.
Consulte también
Comentarios
https://aka.ms/ContentUserFeedback.
Próximamente: A lo largo de 2024 iremos eliminando gradualmente GitHub Issues como mecanismo de comentarios sobre el contenido y lo sustituiremos por un nuevo sistema de comentarios. Para más información, vea:Enviar y ver comentarios de