El programa da un error de tiempo de ejecución porque vararg promueve automáticamente char a int, y debería haber usado int en este caso.
Cuáles son todos los tipos permitidos cuando uso vararg, cómo saber qué tipo usar y evitar tales errores de tiempo de ejecución.
Jeje, GCC dice, “advertencia: ‘char’ se promociona a ‘int’ cuando pasa por ‘…'”. Agradable.
– KerrekSB
16 de agosto de 2011 a las 20:55
En display(4, 'A', 'a', 'b', 'c'); hay 5 ints; no 1 int y 4 chars como pareces creer 🙂
– pmg
16 de agosto de 2011 a las 20:57
@Kerrek: dice que para la expresión va_arg(ptr, char)no la llamada a la display función — donde no hay chars 🙂
– pmg
16 de agosto de 2011 a las 21:02
@pmg: Ah, de hecho, ese es uno de los cambios de C a C ++: en C, los literales de caracteres son números enteros … Nunca supe que no podía usar caracteres de forma variable. wchar_t tampoco funciona, y tampoco char16_t o char32_t (todos son ascendidos a unsigned int).
– KerrekSB
16 de agosto de 2011 a las 21:05
Esto probablemente depende de la longitud de palabra del compilador/máquina. Incluso podría redefinir va_arg para tener esto en cuenta.
– Quentin Reino Unido
16 de agosto de 2011 a las 21:09
otro caso que los demás olvidaron mencionar son los tipos de puntero, crítico es NULL En particular. Dado que esto podría expandirse a 0 o (void*)0 (o algunas otras cosas raras) no sabrá si el compilador pone un int o un void* en la lista. Dado que estos pueden tener un ancho diferente, esto puede provocar errores molestos.
Sí, esa es siempre una fuente sutil de errores. GCC es agradable y se expande NULL para __nullptr en lugar de 0, por lo que no se encontrará con ese error con GCC, pero otros compiladores no son tan buenos. El estándar C solo requiere que NULL expanda a una “constante de puntero nulo definida por la implementación”, que es “una expresión constante entera con el valor 0, o una expresión de este tipo convertida al tipo void*.
– Adam Rosenfield
16 de agosto de 2011 a las 23:02
R.. GitHub DEJAR DE AYUDAR A ICE
Puede utilizar cualquier tipo estándar con va_arg excepto char, signed char, unsigned char, short, unsigned short, _Booly float. Es posible que una implementación defina tipos adicionales no estándar que también tengan un rango de conversión de enteros inferior a into tipos de coma flotante pequeños no estándar, pero no necesitaría conocerlos a menos que tenga la intención de usarlos, por lo que, para fines prácticos, la lista que di está completa.
Alaska
Al usar va_arg el char es ascendido a int. Hay otros tipos (la lista proporcionada por @R..) que se promocionan.
así que para leerlo como un char tienes que hacer typecast.
Esta web utiliza cookies propias y de terceros para su correcto funcionamiento y para fines analíticos y para mostrarte publicidad relacionada con sus preferencias en base a un perfil elaborado a partir de tus hábitos de navegación. Al hacer clic en el botón Aceptar, acepta el uso de estas tecnologías y el procesamiento de tus datos para estos propósitos.
Configurar y más información
Jeje, GCC dice, “advertencia: ‘char’ se promociona a ‘int’ cuando pasa por ‘…'”. Agradable.
– KerrekSB
16 de agosto de 2011 a las 20:55
En
display(4, 'A', 'a', 'b', 'c');
hay 5int
s; no 1int
y 4char
s como pareces creer 🙂– pmg
16 de agosto de 2011 a las 20:57
@Kerrek: dice que para la expresión
va_arg(ptr, char)
no la llamada a ladisplay
función — donde no haychar
s 🙂– pmg
16 de agosto de 2011 a las 21:02
@pmg: Ah, de hecho, ese es uno de los cambios de C a C ++: en C, los literales de caracteres son números enteros … Nunca supe que no podía usar caracteres de forma variable.
wchar_t
tampoco funciona, y tampocochar16_t
ochar32_t
(todos son ascendidos aunsigned int
).– KerrekSB
16 de agosto de 2011 a las 21:05
Esto probablemente depende de la longitud de palabra del compilador/máquina. Incluso podría redefinir va_arg para tener esto en cuenta.
– Quentin Reino Unido
16 de agosto de 2011 a las 21:09