Antwort
Die Variable $phone_missing
ist eine Zeichenfolge, die zufällig false
enthält. Eine nicht leere Zeichenfolge ergibt true
. Siehe auch http://www.linuxintro.org/wiki/Babe#empty_strings
Kommentare
- Ah in Ordnung. Ich hätte diese Variable als boolesch deklariert (zumindest nicht mit dem Deklarationswort), aber die Aschekonsole ließ mich nicht '. Ich möchte auch ' Strings nicht vergleichen. Wie wird das richtig gemacht?
- stackoverflow.com/questions/2953646/… , Aber Vorsicht: Dieser Typ führt eine Zeichenfolgenvariable aus und sowohl falsch als auch wahr sind Unix-Befehle.
Antwort
Ich verwende oft „true“ und „false“, da es sich auch um Befehle handelt, die lediglich Erfolg bzw. Misserfolg zurückgeben. Dann können Sie
if "$phone_missing"; then ...
Antwort
Hier ist eine Möglichkeit Dies unter Beibehaltung der True / False-Werte.
phone_missing=false if [ "$phone_missing" != false ]; then echo "phone_missing is not "false" (but may be non-true, too)" fi if [ "$phone_missing" == true ]; then echo "phone_missing is true." fi
Die doppelten Anführungszeichen $phone_missing
soll vor dem Fall schützen, dass die Variable phone_missing
überhaupt nicht definiert ist. Eine andere gebräuchliche Redewendung, um dies zu verhindern, ist [ x$phone_missing != xfalse ]
, aber die Anführungszeichen erscheinen mir natürlicher.
Der Hinweis befindet sich auf der Hilfeseite bash
für test
:
STRING True if string is not empty. ... ! EXPR True if expr is false.
Im Grunde genommen ist [ $foo ]
wahr, wenn $foo
nicht leer ist. Nicht wahr oder falsch, nur nicht leer. [ ! $foo ]
ist wahr, wenn $ foo leer oder undefiniert ist.
Sie können Ihren Code jederzeit so ändern, dass phone_missing
auf non gesetzt wird -leerer Wert e, was wahr bedeutet. Wenn phone_missing
nicht gesetzt ist (oder leer ist – phone_missing=""
), ist dies falsch. Andernfalls sollten Sie die Operatoren zum Testen von Zeichenfolgen verwenden (=
und !=
).
Das andere kleine Problem ist die Zuordnung. Sie haben es als $phone_missing=true
, während es phone_missing=true
(kein Dollarzeichen) sein sollte.
Entschuldigung, wenn dies der Fall ist ein bisschen dicht, es liegt daran, dass ich bin. Es war ein langer Tag. 🙂
Antwort
Andere Antworten gaben Ihnen eine Lösung, aber ich werde erklären, was mit dem ursprünglichen Denken falsch war.
Bash-Variablen haben keine Typen, daher gibt es keine boolesche Variable oder einen Wert wie true oder false. Grundsätzlich sind alle Bash-Variablen nur Zeichenfolgen.
Wenn Sie eine Variable / Zeichenfolge in Bash testen, ohne den Testtyp anzugeben (-n
oder ) wird standardmäßig ein -n
-Test (Zeichenfolge ungleich Null) verwendet.
Also [ "$var" ]
entspricht [ -n "$var" ]
. Solange $var
mindestens 1 Zeichen enthält, wurde es als wahr ausgewertet.
Da Sie den Ausdruck negiert haben, [ ! "$var" ]
entspricht [ ! -n "$var" ]
. Wenn also $var
mindestens 1 Zeichen enthält, ist der Ausdruck falsch.
Da false
(was gerecht ist) eine Zeichenfolge) enthält 5 Zeichen, der Ausdruck ist falsch. Wenn es keine Rolle spielt, welche Zeichenfolge Sie phone_missing
auf (true
, 0, 1) setzen, lautet der Ausdruck immer false
, weil phone_missing
eine Länge ungleich Null ist. Die einzige Möglichkeit, true
zu erstellen, ist phone_missing=""
, da dies die Länge Null ist.
Antwort
Verwenden Sie keine Zeichenfolge für Boolesche Werte. Verwenden Sie eine Ganzzahl.
Eingabe:
val=1 ((val)) && echo "true" || echo "false" val=0 ((val)) && echo "true" || echo "false"
Ausgabe:
true false
Quelle :
((Ausdruck))
Der Ausdruck wird gemäß den unten unter ARITHMETISCHE BEWERTUNG beschriebenen Regeln ausgewertet. Wenn der Wert des Ausdrucks nicht Null ist, ist der Rückgabestatus 0; Andernfalls lautet der Rückgabestatus 1. Dies entspricht genau dem Ausdruck „Ausdruck“.
Antwort
Ich hätte dies als Kommentar zur Unterstützung von James getan Ko hatte aber nicht den Repräsentanten, um zu kommentieren oder öffentlich abzustimmen.
Das Problem hierbei ist, dass die Klammern [] die Notation für einen Vergleichstest wie Wert oder Zeichenfolgengleichheit sind.
Die Wahrhaftigkeit der Zeichenfolge in Bash für eine leere Zeichenfolge lautet ""
(leere Zeichenfolge) wird als falsch (Rückgabewert 1) und jede nicht leere Zeichenfolge als „falsch“ „wahr ausgewertet „oder“ bob „s dein Onkel“ wird als wahr ausgewertet (Rückgabewert 0).
Sie können sich dies selbst beweisen mit:
if [ "foo" ]; then echo true is $?; else echo false is $?; fi
Die obige $?
ist eine spezielle Variable, die den Status zum Beenden der letzten Befehle enthält (0 Erfolg und eine beliebige> 0 für Fehlercode) und true is 0
. Sie können "foo"
durch alles ersetzen, was Sie möchten. Das Ergebnis ist das gleiche, außer wenn Sie es durch eine leere Zeichenfolge ersetzen. ""
oder ""
In diesem Fall wird die else-Bedingung ausgewertet und false is 1
ausgegeben.
Bei Verwendung von [ ] Klammern die interne Anweisung wie! $ phone_missing wird ausgewertet und geben dann ein 0
für true oder 1
für false an die if-Steuerung zurück l Aussage. Da die Klammer Zeichenfolgen- und Wertevergleiche auswertet, wird $ phone_missing zuerst auf die nicht leere Zeichenfolge „false“ erweitert, die von [] als nicht leere Zeichenfolge (oder true) und dann als! Invertiert das Ergebnis, was dazu führt, dass die if-Anweisung einen falschen Wert (oder Rückgabewert 1) erhält, und überspringt den Bedingungskörper, der die else-Anweisung ausführt, falls vorhanden.
Wie James Ko sagte, wäre die Notation, einfach die zu übergeben Variable, die Ihren „Booleschen Wert“ für die if-Steueranweisung enthält. Beachten Sie , dass in bash ein boolesches wahr und falsch klein geschrieben werden muss wie in: bool_true = true bool_false = false Jeder andere Fall wird als Zeichenfolgen und nicht als boolesch bewerten.
Wenn Sie also Ihr Beispiel und die Antwort von James Ko verwenden, lautet dies:
phone_missing=false echo "missing $phone_missing" if ! $phone_missing then echo "Lost phone at $readabletime" $phone_missing=true fi
oder als ich bevorzugen Sie die Lesbarkeit (syntaktisch gleich und James Ko „s)
phone_missing=false echo "missing $phone_missing" if ( ! $phone_missing ); then echo "Lost phone at $readabletime" $phone_missing=true fi
Andere Antworten wie von Alexios überprüfen buchstäblich den Inhalt der Zeichenfolge. Damit würde eine der folgenden Aussagen zu false führen:
phone_missing=false if [ "$phone_missing" != false ]; then echo "phone_missing is not "false" (but may be non-true, too)" fi if [ "$phone_missing" == true ]; then echo "phone_missing is not "false" (but may be non-true, too)" fi if [ "$phone_missing" == Bobs_your_uncle ]; then echo "phone_missing is not "false" (but may be non-true, too)" fi
Antwort
Die korrekte Syntax lautet if ! $bool; then [statements]; fi
.
Beispiel:
bool=false if ! $bool; then echo "This is correct!" fi if [ ! $bool ]; then echo "This is wrong!" fi
Ausgabe: This is correct!
Kommentare
- Ihre Antwort enthält einen Kern der Wahrheit, aber ohne Erklärung verursacht sie mehr Verwirrung als es Abhilfe schafft. Es ist auch kaum mehr als eine Wiederholung einer der vorherigen Antworten. Wenn Sie nicht möchten, dass Ihre Antwort entfernt wird, erklären Sie, warum sie richtig ist.