2016-11-25 4 views
1

Mein Shell-Name ist test.sh, und ich möchte alle Parameter ausgeben, die an test.sh übergeben werden, aber ich finde, dass mein Code nicht gut funktionieren kann.Wie Skriptparameter sequenziell drucken?

#!/bin/bash 
i=1 
num=$# 
while [ $i -le $num ]; do 
    echo $($i) 
    ((i++)) 
done 

Als ich ./test.sh -a -b -c laufen, meine erwartete Ausgabe ist:

-a 
-b 
-c 

aber es sagt mir

./test.sh: line 5: 1: command not found 
./test.sh: line 5: 2: command not found 
./test.sh: line 5: 3: command not found 

Wie kann ich dieses Problem beheben und Ausgabe aller Parameter mit echo Befehl?

+0

'echo I' $ nur Ausgang' 1 2 3', aber meine Erwartung ist '-a -b -c'. – user6064254

+0

Eigentlich möchte ich 'echo $ ($ i)' verwenden, um das gleiche Ergebnis mit 'echo $ 1 $ 2 $ 3' zu erreichen, aber ich finde 'echo $ ($ i) 'ist ein ungültiger Befehl. – user6064254

Antwort

3

Sie suchen variable indirection:

#!/bin/bash 
i=1 
num=$# 
while [ $i -le $num ]; do 
    echo ${!i}   # <--- print the content of $1, $2... 
    ((i++)) 
done 

Bei der Ausführung dieses zurückgibt:

$ bash test.sh -a -b "-c d" 
-a 
-b 
-c d 

Von Bash Reference Manual → 3.5.3 Shell Parameter Expansion:

Wenn das erste Zeichen des Parameters ein Ausrufezeichen (!) und Parameter ist kein nameRef, es führt eine Ebene der variablen Indirektion ein. Bash verwendet den Wert der aus dem Rest des Parameters gebildeten Variablen als Namen der Variablen; Diese Variable wird dann erweitert, und dieser Wert wird im Rest der Substitution anstelle des Werts Parameter selbst verwendet. Dies ist als indirekte Erweiterung bekannt. Wenn der Parameter ist, wird die Namenserweiterung auf den Namen der Variablen erweitert, auf die von Parameter verwiesen wird, anstatt die vollständige indirekte Erweiterung auszuführen. Die Ausnahmen davon sind die Erweiterungen von $ {! Prefix *} und $ {! Name [@]}, die unten beschrieben werden. Das Ausrufezeichen muss unmittelbar der linken Klammer folgen, um eine Indirektion einzuführen.

Wenn Sie es ausführlicher machen wollen, zeigen die Zuordnung von ${1..n} auf seinen Wert:

#!/bin/bash 
i=1 
num=$# 
while [ $i -le $num ]; do 
    printf "$%s = %s\n" "$i" "${!i}" 
    ((i++)) 
done 

den Ausgang Siehe:

$ bash test.sh -a -b "-c d" 
$1 = -a 
$2 = -b 
$3 = -c d 
+1

ein Shell-Experte, das löst mein Problem, vielen Dank. – user6064254

1

In Bash $(...) die Sequenz zu erstellen eine Sub-Shell, um einen Befehl auszuführen. Es ist eine "neue" Art, Backticks zu verwenden.

Der Ausdruck

$($i) 

ist

`$i` 

So zu

gleichwertig, was Sie tun in einer Unterschale, die Argumente als Befehl aufruft.

+0

Also versucht er, '1',' 2' und '3' als Befehle auszuführen, was nicht der Fall ist. Schön erklärt. – fedorqui

0

Sie können auch eine einzeilige Skript

#!/bin/bash 
echo $* 
Verwandte Themen