Es posible que desee comenzar con mi libro Learning Perl . Es más fácil que adivinar qué hacer hasta que lo hagas bien (monos, máquinas de escribir y Hamlet, y todo eso). :)
brian d foy
Respuestas:
285
En Perl, lo siguiente se evalúa como falso en condicionales:
0'0'undef''# Empty scalar()# Empty list('')
Lo demás es verdad. No hay palabras vacías para trueo false.
@BlueWaldo: también puede usar cmp y <=> al comparar y asignar los resultados de la comparación a un escalar. $ var = $ var1 cmp $ var2; 'cmp' y '<=>' (usado para comparaciones numéricas) devuelve -1, 0 o 1 si el argumento izquierdo es menor, igual o mayor que el argumento derecho. No es booleano, pero a veces es posible que desee saber si un argumento es igual o menor o mayor que el otro en lugar de simplemente igual o no igual.
user118435
99
Problema 1: una lista vacía no es falsa, ya que es imposible verificar si una lista es verdadera o falsa. Se devuelve una lista vacía en contexto escalar undef.
ikegami
44
Problema 2: ('')y ''son del mismo valor. Creo que quería implicar una lista con un elemento que consiste en una cadena vacía (aunque los padres no crean listas), pero como ya he mencionado, es imposible verificar si una lista es verdadera o falsa.
ikegami
66
Problema 3: Los objetos con un operador booleano sobrecargado también pueden ser falsos.
ikegami
15
@eternicode, Perl tiene dos valores específicos que usa cuando necesita devolver verdadero y falso, por lo que no solo tiene booleanos, tiene verdadero ( !0aka PL_sv_yes) y falso ( !1aka PL_sv_no). ¿O estás diciendo que Perl debería croar cada vez que se pruebe la veracidad de algo distinto a estos dos valores? Eso sería completamente horrible. por ejemplo, evitaría$x ||= $default;
ikegami
71
La definición más completa y concisa de falso que he encontrado es:
Todo lo que se convierte en cadena vacía o cadena 0es falso. Todo lo demás es verdad.
Por lo tanto, los siguientes valores son falsos:
La cadena vacía
Valor numérico cero
Un valor indefinido
Un objeto con un operador booleano sobrecargado que evalúa uno de los anteriores.
Una variable mágica que se evalúa como una de las anteriores en la búsqueda.
Tenga en cuenta que una lista vacía literal se evalúa como un valor indefinido en contexto escalar, por lo que se evalúa como algo falso.
Una nota sobre "ceros verdaderos"
Mientras que los números que se encadenan 0son falsos, las cadenas que se numeran a cero no son necesariamente. Las únicas cadenas falsas son 0y la cadena vacía. Cualquier otra cadena, incluso si se numera a cero, es verdadera.
Las siguientes son cadenas que son verdaderas como un booleano y cero como un número:
Sin peligro:
"0.0"
"0E0"
"00"
"+0"
"-0"
" 0"
"0\n"
".0"
"0."
"0 but true"
"\t00"
"\n0e1"
"+0.e-9"
Con una advertencia:
Cualquier cadena para la cual Scalar::Util::looks_like_numberdevuelve falso. (por ejemplo "abc")
si entendí bien la palabra verdadero en Mientras que los números que se convierten en cadena a 0 son verdaderos, deben ser falsos o (para evitar confusiones) evaluar a falsos .
Dmitry Korolyov
1
Su definición "concisa" es inconsistente con su explicación más larga. Considere lo siguiente: my $value = do { package XXX; use overload q[""] => sub { "XXX" }, q[bool] => sub { 0 }; bless [] };. Ahora $valuese stringificará a "XXX" pero se boolifica a falso.
tobyink
1
@tobyink, la versión concisa no es perfecta, simplemente la mejor que he encontrado. Está destinado a ser práctico, no lo abarca todo. Tenga en cuenta que el valor devuelto por su boolhace stringify a 0. Además, no se recomienda crear sobrecargas inconsistentes, y los valores que devuelve podrían considerarse tales. (por ejemplo, una &&puede ser optimizada en una ||, así que si éstos fueran incompatibles, tendría un problema.)
Ikegami
No estoy seguro si 0x00está cubierto aquí.
Zaid
@Zaid, ¿Te refieres al valor devuelto por el código 0x00(el valor numérico cero) o la cadena 0x00(para la cual looks_like_numberes falso)? De cualquier manera, ya está cubierto.
ikegami
59
Perl no tiene un tipo booleano nativo, pero puede usar la comparación de enteros o cadenas para obtener el mismo comportamiento. El ejemplo de Alan es una buena manera de hacerlo usando la comparación de enteros. Aquí hay un ejemplo
my $boolean =0;if( $boolean ){print"$boolean evaluates to true\n";} else {print"$boolean evaluates to false\n";}
Una cosa que he hecho en algunos de mis programas es agregar el mismo comportamiento usando una constante:
Las líneas marcadas en "usar constante" definen una constante llamada true que siempre se evalúa en 1, y una constante llamada false que siempre se evalúa en 0. Debido a la forma en que las constantes se definen en Perl, las siguientes líneas de código también fallan:
true =0;
true = false;
El mensaje de error debería decir algo como "No se puede modificar la constante en la asignación escalar".
Vi eso en uno de los comentarios que preguntaste sobre la comparación de cadenas. Debe saber que debido a que Perl combina cadenas y tipos numéricos en variables escalares, tiene una sintaxis diferente para comparar cadenas y números:
my $var1 ="5.0";my $var2 ="5";print"using operator eq\n";if( $var1 eq $var2 ){print"$var1 and $var2 are equal!\n";} else {print"$var1 and $var2 are not equal!\n";}print"using operator ==\n";if( $var1 == $var2 ){print"$var1 and $var2 are equal!\n";} else {print"$var1 and $var2 are not equal!\n";}
La diferencia entre estos operadores es una fuente muy común de confusión en Perl.
Usar las constantes como macros de un hombre pobre de esa manera es peligroso. Estos ejemplos de código no son equivalentes: if ($exitstatus) { exit; }vs if ($exitstatus == true) { exit; }, que podría no ser obvio para un observador casual. (Y sí, el último ejemplo es un estilo de programación pobre, pero eso no viene al caso).
Zano el
16
Recomiendo use boolean;. Sin embargo, debe instalar el módulo booleano desde cpan.
En Perl, como en la vida, hay muchas verdades. A los inexpertos les gusta escribir cosas tontas como if ($my_true_value == true). Pretender que existe una Verdadera Verdad es, en mi experiencia, un camino hacia el dolor y un código ineficiente.
tjd
2
Perl es filosófico por naturaleza
ILMostro_7
13
Mis favoritos siempre han sido
use constant FALSE =>1==0;use constant TRUE => not FALSE;
que es completamente independiente de la representación interna.
Mala respuesta, pero una fuente fuerte y de buena reputación en perlmonks.org. Sería bueno tener contenido real en lugar de un comentario y un enlace. : - /
ILMostro_7
0
use el siguiente prefijo de archivo, esto agregará a su script perl eTRUE y eFALSE, en realidad será REAL (!) verdadero y falso (al igual que java)
#!/usr/bin/perluse strict;use warnings;use constant {#real true false, compatible with encode_json decode_json for later (we don't want field:false... will be field:0...)
eTRUE => bless(do{\(my $o =1)},'JSON::PP::Boolean'),
eFALSE => bless(do{\(my $o =0)},'JSON::PP::Boolean')};
En realidad, hay algunas razones por las que deberías usar eso.
Mi razón es que al trabajar con JSON, tengo 0 y 1 como valores para las claves, pero este truco se asegurará de que se mantengan los valores correctos a lo largo de su secuencia de comandos.
Respuestas:
En Perl, lo siguiente se evalúa como falso en condicionales:
Lo demás es verdad. No hay palabras vacías para
true
ofalse
.fuente
undef
.('')
y''
son del mismo valor. Creo que quería implicar una lista con un elemento que consiste en una cadena vacía (aunque los padres no crean listas), pero como ya he mencionado, es imposible verificar si una lista es verdadera o falsa.!0
akaPL_sv_yes
) y falso (!1
akaPL_sv_no
). ¿O estás diciendo que Perl debería croar cada vez que se pruebe la veracidad de algo distinto a estos dos valores? Eso sería completamente horrible. por ejemplo, evitaría$x ||= $default;
La definición más completa y concisa de falso que he encontrado es:
Por lo tanto, los siguientes valores son falsos:
Tenga en cuenta que una lista vacía literal se evalúa como un valor indefinido en contexto escalar, por lo que se evalúa como algo falso.
Una nota sobre "ceros verdaderos"
Mientras que los números que se encadenan
0
son falsos, las cadenas que se numeran a cero no son necesariamente. Las únicas cadenas falsas son0
y la cadena vacía. Cualquier otra cadena, incluso si se numera a cero, es verdadera.Las siguientes son cadenas que son verdaderas como un booleano y cero como un número:
"0.0"
"0E0"
"00"
"+0"
"-0"
" 0"
"0\n"
".0"
"0."
"0 but true"
"\t00"
"\n0e1"
"+0.e-9"
Scalar::Util::looks_like_number
devuelve falso. (por ejemplo"abc"
)fuente
my $value = do { package XXX; use overload q[""] => sub { "XXX" }, q[bool] => sub { 0 }; bless [] };
. Ahora$value
se stringificará a "XXX" pero se boolifica a falso.bool
hace stringify a0
. Además, no se recomienda crear sobrecargas inconsistentes, y los valores que devuelve podrían considerarse tales. (por ejemplo, una&&
puede ser optimizada en una||
, así que si éstos fueran incompatibles, tendría un problema.)0x00
está cubierto aquí.0x00
(el valor numérico cero) o la cadena0x00
(para la cuallooks_like_number
es falso)? De cualquier manera, ya está cubierto.Perl no tiene un tipo booleano nativo, pero puede usar la comparación de enteros o cadenas para obtener el mismo comportamiento. El ejemplo de Alan es una buena manera de hacerlo usando la comparación de enteros. Aquí hay un ejemplo
Una cosa que he hecho en algunos de mis programas es agregar el mismo comportamiento usando una constante:
Las líneas marcadas en "usar constante" definen una constante llamada true que siempre se evalúa en 1, y una constante llamada false que siempre se evalúa en 0. Debido a la forma en que las constantes se definen en Perl, las siguientes líneas de código también fallan:
El mensaje de error debería decir algo como "No se puede modificar la constante en la asignación escalar".
Vi eso en uno de los comentarios que preguntaste sobre la comparación de cadenas. Debe saber que debido a que Perl combina cadenas y tipos numéricos en variables escalares, tiene una sintaxis diferente para comparar cadenas y números:
La diferencia entre estos operadores es una fuente muy común de confusión en Perl.
fuente
use warnings;
en lugar de#! perl -w
if ($exitstatus) { exit; }
vsif ($exitstatus == true) { exit; }
, que podría no ser obvio para un observador casual. (Y sí, el último ejemplo es un estilo de programación pobre, pero eso no viene al caso).Recomiendo
use boolean;
. Sin embargo, debe instalar el módulo booleano desde cpan.fuente
if ($my_true_value == true)
. Pretender que existe una Verdadera Verdad es, en mi experiencia, un camino hacia el dolor y un código ineficiente.Mis favoritos siempre han sido
que es completamente independiente de la representación interna.
fuente
Encontré un tutorial que tiene una buena explicación sobre qué valores son verdaderos y falsos en Perl . Establece que:
Los siguientes valores escalares se consideran falsos:
undef
- el valor indefinido0
el número 0, incluso si lo escribe como 000 o 0.0''
La cuerda vacía.'0'
la cadena que contiene un solo dígito 0.Todos los demás valores escalares, incluidos los siguientes, son verdaderos:
1
cualquier número que no sea 0' '
la cuerda con un espacio en ella'00'
dos o más 0 caracteres en una cadena"0\n"
un 0 seguido de una nueva línea'true'
'false'
Sí, incluso la cadena 'falso' se evalúa como verdadero.Hay otro buen tutorial que explica acerca de Perl verdadero y falso .
fuente
Hermosa explicación dada por bobf para los valores booleanos: ¿ Verdadero o falso? Una guía de referencia rápida
Pruebas de verdad para diferentes valores.
fuente
use el siguiente prefijo de archivo, esto agregará a su script perl eTRUE y eFALSE, en realidad será REAL (!) verdadero y falso (al igual que java)
En realidad, hay algunas razones por las que deberías usar eso.
Mi razón es que al trabajar con JSON, tengo 0 y 1 como valores para las claves, pero este truco se asegurará de que se mantengan los valores correctos a lo largo de su secuencia de comandos.
fuente