Ich möchte mehrere Bedingungen wie folgt darstellen:
if [ ( $g -eq 1 -a "$c" = "123" ) -o ( $g -eq 2 -a "$c" = "456" ) ]
then
echo abc;
else
echo efg;
fi
aber wenn ich das Skript ausführte, wird es angezeigt
syntax error at line 15: `[' unexpected,
in Zeile 15 wird angezeigt, ob ....
Was ist daran falsch? Ich denke, mit dem ()
stimmt etwas nicht.
Klassische Technik (Escape-Metazeichen):
if [ \( "$g" -eq 1 -a "$c" = "123" \) -o \( "$g" -eq 2 -a "$c" = "456" \) ]
then echo abc
else echo efg
fi
Ich habe die Verweise auf $g
in doppelte Anführungszeichen gesetzt. Das ist im Allgemeinen eine gute Praxis. Streng genommen werden die Klammern nicht benötigt, weil -a
und -o
Vorrang haben, auch wenn sie vorkommen.
Beachten Sie, dass die Operatoren -a
und -o
Bestandteil der POSIX-Spezifikation für test
, alias [
sind, hauptsächlich aus Gründen der Abwärtskompatibilität (da sie zum Beispiel in 7. Edition UNIX Bestandteil von test
waren), sie jedoch ausdrücklich als gekennzeichnet sind "veraltet" von POSIX. Bash (siehe bedingte Ausdrücke ) scheint die klassische Bedeutung und die POSIX-Bedeutung von -a
und -o
mit eigenen alternativen Operatoren, die Argumente annehmen, zu unterdrücken.
Mit etwas Sorgfalt können Sie den moderneren [[
-Operator verwenden. Beachten Sie jedoch, dass die Versionen in Bash und Korn Shell (zum Beispiel) nicht identisch sein müssen.
for g in 1 2 3
do
for c in 123 456 789
do
if [[ ( "$g" -eq 1 && "$c" = "123" ) || ( "$g" -eq 2 && "$c" = "456" ) ]]
then echo "g = $g; c = $c; true"
else echo "g = $g; c = $c; false"
fi
done
done
Beispiellauf mit Bash 3.2.57 unter Mac OS X:
g = 1; c = 123; true
g = 1; c = 456; false
g = 1; c = 789; false
g = 2; c = 123; false
g = 2; c = 456; true
g = 2; c = 789; false
g = 3; c = 123; false
g = 3; c = 456; false
g = 3; c = 789; false
Sie müssen die Variablen nicht wie in [[
in [
zitieren, da es sich nicht um einen separaten Befehl handelt, der in der gleichen Weise wie [
ist.
Ist das nicht eine klassische Frage?
Das hätte ich gedacht. Es gibt jedoch eine andere Alternative, nämlich:
if [ "$g" -eq 1 -a "$c" = "123" ] || [ "$g" -eq 2 -a "$c" = "456" ]
then echo abc
else echo efg
fi
Wenn Sie die "Portable Shell" -Richtlinien für das autoconf
-Tool oder die zugehörigen Pakete lesen, empfehlen sie diese Notation - mit "||
" und "&&
". Ich denke, Sie könnten sogar so weit gehen:
if [ "$g" -eq 1 ] && [ "$c" = "123" ]
then echo abc
Elif [ "$g" -eq 2 ] && [ "$c" = "456" ]
then echo abc
else echo efg
fi
Wenn die Aktionen so trivial sind wie das Echo, ist das nicht schlecht. Wenn der zu wiederholende Aktionsblock mehrere Zeilen enthält, ist die Wiederholung zu schmerzhaft und eine der früheren Versionen ist vorzuziehen - oder Sie müssen die Aktionen in eine Funktion einschließen, die in den verschiedenen then
-Blöcken aufgerufen wird.
In Bash:
if [[ ( $g == 1 && $c == 123 ) || ( $g == 2 && $c == 456 ) ]]
Mit /bin/bash
wird folgendes funktionieren:
if [ "$option" = "Y" ] || [ "$option" = "y" ]; then
echo "Entered $option"
fi
Seien Sie vorsichtig, wenn Sie Leerzeichen in Ihren String-Variablen haben und nach Existenz suchen. Stellen Sie sicher, dass Sie sie richtig zitieren.
if [ ! "${somepath}" ] || [ ! "${otherstring}" ] || [ ! "${barstring}" ] ; then
$ g=3
$ c=133
$ ([ "$g$c" = "1123" ] || [ "$g$c" = "2456" ]) && echo "abc" || echo "efg"
efg
$ g=1
$ c=123
$ ([ "$g$c" = "1123" ] || [ "$g$c" = "2456" ]) && echo "abc" || echo "efg"
abc
#!/bin/bash
current_usage=$( df -h | grep 'gfsvg-gfslv' | awk {'print $5'} )
echo $current_usage
critical_usage=6%
warning_usage=3%
if [[ ${current_usage%?} -lt ${warning_usage%?} ]]; then
echo OK current usage is $current_usage
Elif [[ ${current_usage%?} -ge ${warning_usage%?} ]] && [[ ${current_usage%?} -lt ${critical_usage%?} ]]; then
echo Warning $current_usage
else
echo Critical $current_usage
fi