En C y algunos lenguajes similares, comparar expresiones booleanas para igualdad false
o true
es un hábito peligroso.
En C, cualquier expresión escalar (numérica o puntero) se puede utilizar en un contexto booleano, por ejemplo, como la condición de una if
declaración. La regla C if (cond)
es equivalente a if (cond != 0)
, es decir, cero es falso y cualquier valor distinto de cero es verdadero. Si cond
es de tipo puntero, 0
se trata como una constante de puntero nulo; if (ptr)
significa if (ptr != NULL)
.
Esto significa que
if (cond)
y
if (cond == true)
No significan lo mismo . El primero es verdadero si cond
no es cero; el segundo es verdadero solo si es igual a true
, que en C (si tiene #include <stdbool.h>
) es simplemente 1
.
Por ejemplo, la isdigit()
función declarada en <ctype.h>
devuelve un int
valor, 0
si el argumento es un dígito, no cero si no lo es. Puede volver 42
para indicar que la condición es verdadera. La comparación 42 == true
fallará.
Sucede que ese 0
es el único valor considerado falso, por lo que la comparación para igualdad false
funcionará; if (!cond)
y if (cond == false)
hacer lo mismo Pero si vas a aprovechar eso, debes recordar que comparar con false
está bien, y comparar con true
no lo está. Peor aún, la comparación con true
funcionará la mayor parte del tiempo (por ejemplo, los operadores de igualdad y relacionales siempre rinden 0
o 1
). Esto significa que cualquier error que introduzca al usar esto aún podría ser difícil de rastrear. (No se preocupe, aparecerán tan pronto como demuestre el código a un cliente importante).
C ++ tiene reglas ligeramente diferentes; por ejemplo, su bool
tipo está un poco más integrado en el lenguaje y se if (cond)
convierte cond
en tipo bool
. Pero el efecto es (principalmente) el mismo.
Algunos otros idiomas tienen lo que uno podría llamar booleanos con mejor comportamiento, de modo que cond == true
y cond == false
(o lo que sea que sea la sintaxis) es seguro. Aun así, cada idioma que he visto tiene un operador not
u !
; está ahí, así que bien podrías usarlo. Usar en cond == false
lugar de !cond
o not cond
no, en mi opinión, mejora la legibilidad. (Es cierto que el !
personaje puede ser difícil de ver de un vistazo; a veces agrego un espacio después !
para evitar esto).
Y a menudo puede evitar el problema y mejorar la claridad reorganizando ligeramente el código. Por ejemplo, en lugar de:
if (!cond) {
do_this();
}
else {
do_that();
}
podrías escribir:
if (cond) {
do_that();
}
else {
do_this();
}
Eso no siempre es mejor, pero no está de más buscar oportunidades donde está.
Resumen: en C y C ++, las comparaciones de igualdad con true
y false
son peligrosas, excesivamente detalladas y con un estilo pobre. En muchos otros idiomas, tales comparaciones pueden no ser peligrosas, pero siguen siendo demasiado detalladas y de mal estilo.