Welcher Befehl bedeutet "nichts tun" in einer Bedingung in Bash?

180

Manchmal, wenn ich Bedingungen mache, muss der Code nichts tun, z. B. möchte ich, dass Bash nichts tut, wenn er $agrößer als "10" ist, "1" druckt, wenn er $akleiner als "5" ist, andernfalls "2":

if [ "$a" -ge 10 ]
then
elif [ "$a" -le 5 ]
then
    echo "1"
else
    echo "2"
fi

Dies macht jedoch einen Fehler. Gibt es einen Befehl, der nichts bewirkt und mein Skript auch nicht verlangsamt?

Dorf
quelle

Antworten:

340

Der No-Op-Befehl in der Shell lautet :(Doppelpunkt).

if [ "$a" -ge 10 ]
then
    :
elif [ "$a" -le 5 ]
then
    echo "1"
else
    echo "2"
fi

Aus dem Bash-Handbuch :

:(ein Doppelpunkt)
Tun Sie nichts anderes, als Argumente zu erweitern und Umleitungen durchzuführen. Der Rückgabestatus ist Null.

Barmar
quelle
3
@ SaintHax Nein, es läuft nicht true. Es ist in die Shell eingebaut und macht nichts.
Barmar
1
Es ist eine eingebaute Shell (Sie haben Recht), es gibt true (Status 0) zurück, genau wie true, und es ist schwieriger zu lesen. Bash ist eine DevOps-Sprache, und wenn :sie von jemandem in meinem Team geschrieben wird, muss sie geändert werden.
SaintHax
3
@SaintHax Wenn jemand truein einem nicht bedingten Kontext verwendet wird, muss er dies ändern. if trueist in Ordnung, then truescheint falsch.
Barmar
1
Natürlich können Sie den Code einfach neu schreiben, if ! condition; then do something; fianstatt ihn zu verwenden if condition; then :; else do something; fi.
Barmar
Ich stimme mit Ihnen ein. Dieses Beispiel könnte geschrieben werden, wenn / elif / else zusammengesetzte Bedingungen verwendet und besser wäre.
SaintHax
38

Sie können wahrscheinlich nur den trueBefehl verwenden:

if [ "$a" -ge 10 ]; then
    true
elif [ "$a" -le 5 ]; then
    echo "1"
else
    echo "2"
fi

Eine Alternative in Ihrem Beispielfall (aber nicht unbedingt überall) besteht darin, Ihr if / else neu zu bestellen:

if [ "$a" -le 5 ]; then
    echo "1"
elif [ "$a" -lt 10 ]; then
    echo "2"
fi
Schwach
quelle
8
Wenn Sie nicht das Ergebnis testen beide trueund falsesind effektiv nicht-ops , so weit das Skript betrifft, aber im Prinzip sie könnten in einigen Muscheln Gabel , die diese Syntax akzeptiert so vielleicht :besser ist.
dmckee --- Ex-Moderator Kätzchen
3
Die Frage ist mit bash markiert. In Bash trueund falsesind eingebaut. Für ältere Muscheln true, falseund sogar :möglicherweise externe Befehle (obwohl Sie wahrscheinlich die letztere nur in sehen würde sehr alte Muscheln).
Keith Thompson
6
Ich bevorzuge :einfach, weil es expliziter ist, was die Absicht ist
Freedom_Ben
9

Obwohl ich die ursprüngliche Frage zum No-Op-Befehl nicht beantworte, können viele (wenn nicht die meisten) Probleme, bei denen man denkt, " in diesem Zweig muss ich nichts tun ", umgangen werden, indem einfach die Logik so umstrukturiert wird , dass dieser Zweig gewinnt nicht auftreten.

Ich versuche, anhand des OP-Beispiels eine allgemeine Regel anzugeben

Tun Sie nichts, wenn $ a größer als "10" ist. Drucken Sie "1", wenn $ a kleiner als "5" ist. Andernfalls drucken Sie "2".

Wir müssen einen Zweig vermeiden, $ader mehr als 10 bekommt$a < 10 eine allgemeine Bedingung nach der Bedingung auf jede andere angewendet werden kann.

Wenn Sie sagen, dass Sie bei X nichts tun , formulieren Sie es im Allgemeinen so, dass Sie einen Zweig vermeiden, in dem X. . Normalerweise können Sie die Vermeidung erreichen, indem Sie einfach X negieren und auf alle anderen Bedingungen anwenden.

Das OP-Beispiel mit der angewendeten Regel kann also wie folgt umstrukturiert werden:

if [ "$a" -lt 10 ] && [ "$a" -le 5 ]
then
    echo "1"
elif [ "$a" -lt 10 ]
then
    echo "2"
fi

Nur eine Variation der oben genannten, die alles in den $a < 10Zustand einschließt :

if [ "$a" -lt 10 ]
then
    if [ "$a" -le 5 ]
    then
        echo "1"
    else
        echo "2"
    fi
fi

(Für dieses spezielle Beispiel ist die Umstrukturierung von @Flimzys sicherlich besser, aber ich wollte allen Personen, die suchen, wie man nichts tut, eine allgemeine Regel geben.)

KeyNone
quelle
5
Ein Grund, warum jemand ein No-Op haben möchte, ist die anfängliche Strukturierung des Codes mit der Idee, dass man das "später hier etwas hinzufügen" hinzufügt, ohne versehentliche Nebenwirkungen zu haben. Wenn Sie beispielsweise eine Wenn-Dann-Sonst-Fi in eine .bashrc-Datei einfügen, werden echo "put stuff here"einige der Nicht-Login-Verwendungen unterbrochen (z. B. wird scp unterbrochen), und nur Leerzeichen / Kommentare verursachen einen Laufzeitfehler.
Aphoid