Comparación de dos cadenas sin usar ningún tipo de bucle

Iniciado por geeke, 15 Marzo 2015, 19:43 PM

0 Miembros y 1 Visitante están viendo este tema.

geeke

Buenas, no estoy seguro si esto ya es conocido o no pero jugando con una implementación de strcmp descubrí que con solo comparar la dirección de inicio de dos cadenas se podía saber si eran iguales o no

Código (cpp) [Seleccionar]
#include <stdio.h>

int strcmp1(char *s, char *t)
{
    /*for(; *s==*t; s++, t++)
    {
        printf("s = %p, s = %c\n", s, *s);
        printf("t = %p, t = %c\n", t, *t);

        if(*s=='\0')
            return 0;
    }*/
    return s - t;
}

int main(void)
{
    if(strcmp1("hola", "hola") == 0)
        puts("Igual");
    else
        puts("Desigual");

    return 0;
}


Según veo con el depurador las direcciones de las cadenas son iguales sin ambas son iguales caso contrario son diferentes. Siendo sincero no entiendo porque pasa esto dos cadenas diferentes no deberían ocupar la misma dirección al mismo tiempo  :huh: ¿Alguien puede explicar que ocurre aquí?

rir3760

Aquí hay que tener presente la distinción entre contenedor (array) y contenido (cadena).

En el caso de las cadenas literales como "hola" estas se almacenan en un array anónimo (sin nombre) con el tamaño suficiente para cada uno de los caracteres indicados mas el terminador '\0', cadenas literales idénticas pueden almacenarse en arrays distintos o bien solo ser una referencia al (la dirección del) mismo array.

A ello se debe que la comparación "hola" == "hola" puede ser verdadera pero el estándar de C no lo garantiza.

Caso aparte si la cadena se almacena en un array declarado en el programa, en el bloque de memoria retornado por las funciones calloc, malloc o realloc o bien uno de los arrays estáticos parte de la biblioteca estándar de C. En todos esos casos las direcciones de memoria serán distintas sin importar el contenido.

Un saludo
C retains the basic philosophy that programmers know what they are doing; it only requires that they state their intentions explicitly.
--
Kernighan & Ritchie, The C programming language

kutcher

#2
Cita de: CooperJames en 15 Marzo 2015, 19:43 PM
¿Alguien puede explicar que ocurre aquí?

En realidad no funciona solo parece estar funcionado. La razón por la que esto sucede es probablemente debido a una optimización del compilador:  al tratar de reducir los requisitos de memoria ya que las dos cadenas literales son idénticas, por lo que el compilador genera sólo una instancia de ellos y utiliza ese mismo puntero cada vez que se hace referencia a la cadena literal.

Eso es lo que parece suceder en su caso pero el resultado puede variar de compilador a compilador. No se puede confiar en esto, también mencionar que si dejas que el usuario ingrese las cadenas no se almacenaran en la misma dirección, por lo tanto su método no devolverá cero.