2009-06-24 15 views
193

ho provato:Come si usano le variabili booleane in Perl?

$var = false; 
$var = FALSE; 
$var = False; 

nessuno di questi lavori. Ottengo il messaggio di errore

Bareword "false" not allowed while "strict subs" is in use.
+30

Si potrebbe voler iniziare con il mio libro _Learning Perl_. È più facile che indovinare cosa fare fino a quando non lo fai bene (scimmie, macchine da scrivere, e Amleto, e tutto il resto). :) –

risposta

261

In Perl, il seguente valutare a false in condizionali:

0 
'0' 
undef 
'' # Empty scalar 
() # Empty list 
('') 

Il resto sono vere. Non ci sono parole per true o false.

+0

Il confronto corretto, quindi, è un confronto con zero, come in $ var = 0? –

+0

No. 1. = non è un confronto, è un incarico. 2. Fai "if ($ var) {...}". –

+2

@Robert Harvey: 'perl -le 'my $ var = 0; stampa "False" a meno che ($ var); '' –

57

Perl non ha un tipo booleano nativo, ma è possibile utilizzare il confronto di numeri interi o stringhe per ottenere lo stesso comportamento. L'esempio di Alan è un buon modo per farlo usando il confronto tra interi. Ecco un esempio

my $boolean = 0; 
if ($boolean) { 
    print "$boolean evaluates to true\n"; 
} else { 
    print "$boolean evaluates to false\n"; 
} 

Una cosa che ho fatto in alcuni dei miei programmi si aggiunge lo stesso comportamento con una costante:

#!/usr/bin/perl 

use strict; 
use warnings; 

use constant false => 0; 
use constant true => 1; 

my $val1 = true; 
my $val2 = false; 

print $val1, " && ", $val2; 
if ($val1 && $val2) { 
    print " evaluates to true.\n"; 
} else { 
    print " evaluates to false.\n"; 
} 

print $val1, " || ", $val2; 
if ($val1 || $val2) { 
    print " evaluates to true.\n"; 
} else { 
    print " evaluates to false.\n"; 
} 

Le linee segnate in "uso costante" definire una costante di nome vero che restituisce sempre 1, e una costante di nome falso che valuta sempre da 0. a causa del modo in cui le costanti sono definite in Perl, le seguenti righe di codice non riesce così:

true = 0; 
true = false; 

Il messaggio di errore dovrebbe indicare qualcosa come "Impossibile modificare la costante nell'assegnazione scalare".

Ho visto che in uno dei commenti che hai chiesto sul confronto delle stringhe. Si deve sapere che, poiché il Perl combina le stringhe e tipi numerici a variabili scalari, avete sintassi diversa per il confronto di stringhe e numeri:

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 differenza tra questi operatori è una fonte molto comune di confusione in Perl.

+6

-1 ... vedere http://c-faq.com/cpp/slm.html –

+4

'use warnings;' invece di '#! perl -w' –

+10

Utilizzare le costanti come macro di un uomo povero in questo modo è pericoloso. Questi esempi di codice non sono equivalenti: 'if ($ exitstatus) {exit; } 'vs' if ($ exitstatus == true) {exit; } ', che potrebbe non essere ovvio per un osservatore casuale. (E sì, l'ultimo esempio è uno stile di programmazione scadente, ma questo è oltre il punto). – Zano

14

Raccomando use boolean;. Devi installare il modulo boolean da cpan però.

+6

In Perl, come nella vita, ci sono molte verità. L'inesperto piace scrivere cose stupide come 'if ($ my_true_value == true)'. Fingere che ci sia una vera verità è, nella mia esperienza, un percorso verso il dolore e un codice inefficiente. – tjd

+1

Perl è filosofico per natura –

67

Il più completo, definizione sintetica di falso che ho incontrato è:

Tutto ciò che stringifies alla stringa vuota o la stringa `0` è falso. Tutto il resto è vero.

Pertanto, i seguenti valori sono false:

  • La stringa vuota
  • valore numerico pari a zero
  • Un valore indefinito
  • Un oggetto con un operatore booleano overload che valuta uno dei precedenti.
  • Una variabile magica che valuta uno dei precedenti in fetch.

Ricordare che un valore letterale di elenco vuoto restituisce un valore non definito nel contesto scalare, quindi viene valutato come falso.


Una nota sulle "vere" zeri

Mentre i numeri che stringa i per 0 sono false, stringhe che numify a zero non sono necessariamente. Le sole stringhe false sono 0 e la stringa vuota. Qualsiasi altra stringa, anche se numifica a zero, è vera.

Quelle che seguono sono stringhe vere come booleane e zero come numero.

  • Senza un avvertimento:
    • "0.0"
    • "0E0"
    • "00"
    • "+0"
    • "-0"
    • " 0"
    • "0\n"
    • ".0"
    • "0."
    • "0 but true"
    • "\t00"
    • "\n0e1"
    • "+0.e-9"
  • con un avvertimento:
    • Qualsiasi stringa per cui Scalar::Util::looks_like_number restituisce false. (Ad es "abc")
+0

se ho capito bene la parola ** true ** in * Mentre i numeri che stringificano a 0 sono vere * dovrebbero essere ** false ** o (per evitare confusione) ** valutare a false ** . – user907860

+1

La tua definizione "concisa" è incoerente con la tua spiegazione più lunga. Considera: 'my $ value = do {pacchetto XXX; usa overload q [""] => sub {"XXX"}, q [bool] => sub {0}; benedica []}; '. Ora '$ valore' verrà convertito in" XXX "ma boolifica in" falso ". – tobyink

+1

@tobyink, La versione concisa non è perfetta, ma solo la migliore che ho trovato. È pensato per essere pratico, non onnicomprensivo. Prendi nota che il valore restituito dal tuo 'bool' è stringify a' 0'. Inoltre, si è scoraggiati dal creare sovraccarichi incoerenti e i valori restituiti potrebbero essere considerati tali. (ad esempio un '&&' può essere ottimizzato in un '||', quindi se questi fossero incoerenti, avresti un problema.) – ikegami

2

Bella spiegazione data da bobf per i valori booleani: True or False? A Quick Reference Guide

test di verità per valori diversi

     Result of the expression when $var is: 

Expression   | 1  | '0.0' | a string | 0  | empty str | undef 
--------------------+--------+--------+----------+-------+-----------+------- 
if($var)   | true | true | true  | false | false  | false 
if(defined $var) | true | true | true  | true | true  | false 
if($var eq '') | false | false | false | false | true  | true 
if($var == 0)  | false | true | true  | true | true  | true 
+0

Risposta scarso, ma una fonte affidabile e affidabile in perlmonks.org. Sarebbe bello avere dei veri ** contenuti ** invece di un commento e un link. : -/ –

0

utilizzare il seguente prefisso del file, questo aggiungerà al vostro script perl eTRUE ed eFALSE, sarà in realtà REAL (!) vero e falso (proprio come java)

#!/usr/bin/perl 
use 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') 
      }; 

Ci sono, in realtà, alcuni motivi per cui dovresti usarlo.

La ragione è che lavorando con JSON, ho 0 e 1 come valori per le chiavi, ma questo hack assicurerà che i valori corretti siano mantenuti lungo lo script.

7

Mi sono imbattuto in un tutorial che ha una spiegazione chiara su Quali valori sono veri e falsi in Perl.E 'affermare che:

Dopo valori scalari sono considerati falsi:

  • undef - il valore indefinito
  • 0 il numero 0, anche se si scrive come 000 o 0.0
  • '' la stringa vuota .
  • '0' la stringa che contiene una singola cifra 0.

Tutti gli altri valori scalari, tra cui sono vere:

  • 1 qualsiasi non-0 numero
  • ' ' la stringa con uno spazio in esso
  • '00' due o più 0 caratteri una stringa
  • "0\n" a 0 seguito da una nuova riga
  • 'true'
  • 'false' sì, anche la stringa "false" viene valutata su true.

C'è un altro buon tutorial che spiega su Perl true and false.

7

I miei preferiti sono sempre stati

use constant FALSE => 1==0; 
use constant TRUE => not FALSE; 

che è completamente indipendente dalla rappresentazione interna.

+0

Brillante. Hai risolto da solo il linguaggio di programmazione Perl! –

Problemi correlati