Bash-Schleife durch Liste der Zeichenfolgen


12

Ist es möglich, dieses Beispiel zu formatieren:

for i in string1 string2 stringN
do
 echo $i
done

zu etwas ähnlichem:

for i in 
string1
string2
stringN
do
 echo $i
done

EDIT: Entschuldigung für die Verwirrung, wusste nicht, dass es verschiedene Methoden zum Ausführen von Skripten gibt - sh <scriptname>versus bash <scriptname>und auch dieses Ding, das ich momentan nicht benennen kann - #!/bin/shund #!/bin/bash:)


Was ist das Problem, das Sie lösen möchten?
Jesse_b

Haben Sie versucht, was Sie fragen, um zu sehen, ob es funktionieren würde?
DopeGhoti

@ Jesse_b Lesbarkeit und Verwaltbarkeit von Strings

@DopeGhoti ja ich habe

@waayee: In diesem Fall ist ein Array die beste Wahl. Siehe Glenn Jackmans Antwort.
Jesse_b

Antworten:


31

Die Verwendung von Arrays in Bash kann die Lesbarkeit verbessern: Diese Array-Syntax ermöglicht beliebige Leerzeichen zwischen Wörtern.

strings=(
    string1
    string2
    "string with spaces"
    stringN
)
for i in "${strings[@]}"; do
    echo "$i"
done

1
Dies scheint am elegantesten, gibt aber leider Fehler: Syntaxfehler: "(" unerwartet

1
@waayee, dann lässt du es nicht in Bash laufen. Denken Sie daran, dass dies shnicht unbedingt Bash ist und insbesondere nicht unter Debian und Ubuntu.
Ilkkachu

1
@ilkkachu Denke, ich verstehe es jetzt - muss "bash <Skriptname>" ausführen, nicht "sh <Skriptname>" :)

@waayee, oder setzen Sie eine richtige Hashbang / Shebang-Zeile und führen Sie sie wie eine ausführbare Datei aus. Erforderliche Lektüre: Bestimmt der Shebang die Shell, in der das Skript ausgeführt wird?
Ilkkachu

1
@rrrrr, Ihre Fragen werden wahrscheinlich hier beantwortet: stackoverflow.com/q/12314451/7552
Glenn Jackman

4

Sie können dem Zeilenumbruch mit einem Backslash entkommen:

$ for i in \
> hello \
> world
> do
> echo $i
> done
hello
world
$

2

Sie können die Zeilenumbrüche vor / nach jedem Element, über das Sie eine Schleife ausführen, umgehen:

for i in \
    string1 \
    string2 \
    stringN
do
   printf '%s\n' "$i"
done

Oder für dieses einfache Beispiel:

printf '%s\n' string1 string2 stringN

das hat das gleiche Ergebnis.

Verbunden:

Variation mit einem bashArray:

strings=(
    string1
    string2
    stringN
)

printf '%s\n' "${strings[@]}"

1

Wenn ein Wechsel zu möglich zshist:

for string (
  string1
  'other string'
  etc..
) printf '%s\n' "$string"

0

Sie können den hierloop verfügbaren Befehl folgendermaßen verwenden :

$ loop "echo $ITEM" --for string1,string2,string3

oder, wenn Sie eine Liste als Datei haben:

$ cat file_list.txt | loop "echo $ITEM"

0
list='a b c d'
for element in $list;do 
    echo "$element"
done

Ihnen fehlen Semikolons!
41754

Beachten Sie, dass dies funktionieren würde, solange jede Zeichenfolge ein separates Wort ist. Sobald Sie Leerzeichen in Ihren Zeichenfolgen haben, teilen die Leerzeichen die Zeichenfolge in mehrere Wörter auf. Wenn die $listZeichenfolge Dateinamen-Globbing-Zeichen ( list='* * * *') enthält, ersetzt die Shell diese möglicherweise durch übereinstimmende Dateinamen.
Kusalananda

0

Gleiches, weniger Text:

array=(
        string{1..7}
)

for i in "${array[@]}"; do
    echo "$i"
done

string1usw. sind nicht die anzuzeigenden Literalwerte, sondern Platzhalter, sodass dieser Ansatz nicht funktioniert.
Stephen Kitt

wenn ja, warum sich die Mühe machen array ( … )? mach es einfach for i in string{1..7}; do echo "$i"; done; geradeprintf '%s\n' string{1..7}
αғsнιη
Durch die Nutzung unserer Website bestätigen Sie, dass Sie unsere Cookie-Richtlinie und Datenschutzrichtlinie gelesen und verstanden haben.
Licensed under cc by-sa 3.0 with attribution required.