2012-05-11 11 views
5

Duplicar posibles:
How are string literals compiled in C?comparación de direcciones y almacenamiento de cadenas

escribí el pequeño código a continuación. En este código, creo que se compararía la dirección de la primera y la segunda cadena "hola". Estoy confundido en esto. En primer vistazo, pensé que ambas cadenas se almacenarían en la memoria de solo lectura y, por lo tanto, tendrían una dirección diferente. Pero "igual" se imprimió después de la ejecución.

Cuando vi el objdump, no pude ver la cadena de hola. Entiendo que no he tomado una variable para almacenarlos, pero ¿dónde se guardará "hola"?

¿Se almacenará en STACK? o ¿Se almacenará en el segmento de código?

#include<stdio.h> 
int main() 
{ 
    if ("hello" == "hello") 
     printf("\n equal "); 
    else 
     printf("\n not equal"); 
    return 0; 
} 

Cuando cambié la condición if a if ("hello" == "hell1"), "es igual a" se imprimieron. De nuevo, dónde y cómo se almacenan las cadenas. ¿Se almacenará en STACK? o ¿Se almacenará en el segmento de código?

Realmente agradecería que alguien aquí me brinde una respuesta detallada. Gracias

+0

Si ve el desmontaje de esto, se dará cuenta de que no hay equivalente 'if' en absoluto! ¡Salida optimizada! –

+0

posible duplicado de [Una pregunta básica: ¿cómo se compilan los literales de cadena en C?] (Http://stackoverflow.com/q/6680819/), [¿Por qué es "a"! = "A" en C?] (Http : //stackoverflow.com/q/4843640/), [C literales de cadena: ¿a dónde van?] (http://stackoverflow.com/q/2589949/) – outis

Respuesta

3

En su ejemplo particular, las cadenas "hello" ni siquiera son parte del código. El compilador es lo suficientemente inteligente como para detectar que el código siempre y para siempre imprimirá "igual" para que los elimine por completo.

Si el código se parecía a esto, sin embargo:

#include<stdio.h> 
int main() 
{ 
    const char *h1 = "hello"; 
    const char *h2 = "hello"; 
    if (h1 == h2) 
     printf("\n equal "); 
    else 
     printf("\n not equal"); 
    return 0; 
} 

Usted haría aún conseguir "iguales", a pesar de que, sin embargo, en realidad se puede hacer la comparación (cuando se compila sin optimizaciones adicionales). Es una optimización: el compilador detectó que tiene dos cadenas idénticas codificadas y las fusionó en el binario resultante.

Considerando que, si su código se veía así, el compilador no sería capaz de adivinar (por defecto), que son la misma cosa, y verá el mensaje "no es igual":

#include<stdio.h> 
#include<string.h> 
#include<stdlib.h> 

int main() 
{ 
    char *h1 = malloc(sizeof(char) * 10); 
    char *h2 = malloc(sizeof(char) * 10); 

    strcpy(h1, "hello"); 
    strcpy(h2, "hello"); 

    if (h1 == h2) 
     printf("\n equal "); 
    else 
     printf("\n not equal"); 

    free(h1); 
    free(h2); 

    return 0; 
} 
+0

Incluso sin optimización, se ha llevado a cabo un tipo de optimización en el código que muestra. Tanto 'h1' como' h2' apuntan a lo mismo. Creo que no podemos evitar el compilador de optimizaciones básicas incluso en 'O0'? No estoy seguro aunque –

+0

@PavanManjunath He reestructurado mi publicación para que quede más clara. –

+0

Como se trata de una comparación de direcciones, ¿cómo puede el compilador optimizar el código suponiendo que se trata de una comparación de cadenas? –

0

Literales de cadena, ya que sus dos "hello" se pueden realizar en memoria de solo lectura por el compilador y, además, tiene el derecho de realizar uno de esos literales si el valor coincide.

El resultado de su comparación es la implementación definida e incluso puede variar según las diferentes versiones del mismo compilador u otras opciones de optimización que proporcione.

+0

En realidad, en su ejemplo, "hola" no se almacena en '.TEXT' en absoluto. Pero estás en lo correcto para el código modificado en mi publicación. –

+0

@ MahmoudAl-Qudsi, para su compilador este puede ser el caso o no. Este es un detalle de implementación de la plataforma, diferentes compiladores lo harán de manera diferente. –

1

si dos cadenas se comparan si son iguales, como "hola" == "hola", no hay ninguna comparación en general como dijo Pavan Manjunath. el montaje de la siguiente manera:

 
    .file "hello.c" 
    .section .rodata 
.LC0: 
    .string "\n equal " 
    .text 
.globl main 
    .type main, @function 

pero si estos dos cuerdas no es igual, como "hello2" == "hola", a continuación, compilador asigna memoria en.rodata para ellos, parece de accembly, de la siguiente manera:

 
    .file "hello.c" 
    .section .rodata 
.LC0: 
    .string "hello2" 
.LC1: 
    .string "hello" 
Cuestiones relacionadas