Este programa en C da un resultado extraño:
#include <stdio.h> #include <string.h> int main(int argc, char *argv[]) { char str1[5] = "abcde"; char str2[5] = " haha"; printf("%s\n", str1); return 0; }cuando ejecuto este código me sale:
abcde haha Solo quiero imprimir la primera cadena como se puede ver en el código.
¿Por qué imprime ambos?
"abcde" tiene en realidad 6 bytes debido al carácter de terminación nulo en las cadenas C. Cuando haces esto:
char str1[5] = "abcde";No está almacenando el carácter de terminación nulo, por lo que no es una cadena adecuada.
Cuando haces esto:
char str1[5] = "abcde"; char str2[5] = " haha"; printf("%s\n", str1); Da la casualidad de que la segunda cadena se almacena justo después de la primera, aunque esto no es obligatorio. Al llamar a printf en una cadena que no termina en nulo, ya ha causado un comportamiento indefinido.
Actualizar:
Como se indica en los comentarios de clcto, esto se puede evitar al no especificar explícitamente el tamaño de la matriz y dejar que el compilador lo determine en función de la cadena:
char str1[] = "abcde";o use un puntero en su lugar si eso funciona para su caso de uso, aunque no son lo mismo:
const char *str1 = "abcde";Ambas cadenas, str1 y str2 , no tienen terminación nula. Por lo tanto la declaración
printf("%s\n", str1); invocará un comportamiento indefinido.
printf imprime los caracteres en una cadena uno por uno hasta que encuentra un '\0' que no está presente en su cadena. En este caso, printf continúa más allá del final de la cadena hasta que encuentra un carácter nulo en algún lugar de la memoria. En su caso, parece que printf pasa el final de la cadena "abcde" y continúa imprimiendo los caracteres de la segunda cadena " haha" , que por casualidad se encuentra justo después de la primera cadena en la memoria.
Mejor cambiar de bloque
char str1[5] = "abcde"; char str2[5] = " haha";para
char str1[] = "abcde"; char str2[] = " haha";para evitar este problema.
Técnicamente, este comportamiento no es inesperado , es indefinido : su código está pasando un puntero a una cadena C que carece de terminador nulo para printf , que es un comportamiento indefinido.
Sin embargo, en su caso, sucede que el compilador coloca dos cadenas consecutivas en la memoria, por lo que printf se ejecuta en un terminador null después de imprimir str2 , lo que explica el resultado que obtiene.
Si desea imprimir solo la primera cadena, agregue espacio para el terminador nulo, así:
char str1[6] = "abcde";Mejor aún, deje que el compilador calcule el tamaño correcto para usted:
char str1[] = "abcde";