Um den Ablauf einer Kommandoprozedur zu steuern, gibt es - ähnlich wie in Programmen - eine Reihe von Kontrollstrukturen.
Die if - Anweisung
if ( expression ) command
if ( expression ) then command(s) else if ( expression ) then command(s) else command(s) endif
Die if-Anweisung existiert also als einzelne Anweisung oder als if-Block. Ein if-Block kann elseif- und else-Zweige besitzen. Es ist darauf zu achten, dass vor und hinter den runden Klammern mindestens ein Leerzeichen steht.
Beispiel:
#!/bin/csh
#
# Datei: if.csh
# Beispiel zur if-Anweisung
#
# 02.05.97 - WP
#
if ($#argv <= 0) then
echo {$0}: Aufruf ohne Argumente
exit
else
echo {$0}: Es wurden $#argv Argumente uebergeben
endif
exit
Die foreach - Anweisung
foreach var ( wordlist ) command(s) end
Jedes Wort aus der wordlist wird der Variablen var zugewiesen und die command(s) ausgeführt. Die foreach-Schleife wird so oft durchlaufen, wie Elemente in der wordlist enthalten sind.
Beispiele:
#!/bin/csh
#
# Datei: foreach.csh
# Beispiel fuer foreach-Schleife
#
# 02.05.97 - WP
#
foreach dir ($path)
ls $dir
end
Dieses script verwendet in der foreach-Schleife die Variable $path als wordlist. Es werden alle Verzeichnisse gelistet, die im Suchpfad stehen.
#!/bin/csh
#
foreach datei (x1 x2 x3)
echo $datei
echo "$datei enthaelt diese Zeile" > $datei
end
Obiges script legt die drei Dateien namens x1, x2 und x3 an mit jeweils einer Zeile Inhalt.
Die while - Schleife
while ( expression ) command(s) end
Die while-Schleife kann mit numerischen oder string-Variablen benutzt werden. Die Schleife wird solange durchlaufen, bis expression false ist.
#!/bin/csh
#
@ i = 1
while ( $i <= 10 )
echo "$i - te Schleife"
@ i++
end
Für das zeilenweise Einlesen einer Datei eignet sich die while-Schleife in folgender Form:
#!/bin/csh
#
set input = 1
while ( "$input" != "" )
set input = $<
echo "Ausgabe: $input"
end
Die Datei, die ausgelesen werden soll, wird beim Kommandoaufruf mit dem Operator zur Eingabe-Umlenkung übergeben ( script < inputdatei ). Die Datei wird solange gelesen, bis die Variable input leer ist (Dateiende).
Das shift-Statement
shift wirkt auf die Argumentenliste argv shift varname wirkt auf die spezielle Variable
shift verschiebt die Argumente einer wordlist nach links. Das ganz links stehende Argument fällt aus der wordlist heraus.
#!/bin/csh
#
# Datei: shift.csh
# Beispiel fuer shift-Statement
#
set line = $<
set input = ( $line )
foreach element ($input)
echo $input
shift input
end
Fallunterscheidung mit switch und case
switch ( string ) case pattern1: command(s) breaksw case pattern2: command(s) breaksw ... ... default: command(s) breaksw endsw
Es wird nach einer Übereinstimmung von string und pattern gesucht und die dort befindlichen Kommandos ausgeführt. Wird keine Übereinstimmung gefunden, so werden die Kommandos unter default abgearbeitet. Im pattern-string können die pattern-matching character *, ? und [ ] verwendet werden.
#!/bin/csh
#
# Datei: case.csh
# Beispiel fuer case
#
set line = $<
set input = ( $line )
foreach element ($input)
switch ( $element )
case [aA]*:
echo "Name $element beginnt mit einem A"
breaksw
case [hH]*:
echo "Name $element beginnt mit einem H"
breaksw
case [rR][uU][dD][iI]:
echo "Der Name lautet $element"
breaksw
default:
echo "Name interessiert mich nicht"
breaksw
endsw
shift input
end
Die break-Anweisung
Ein break bewirkt den Abbruch der Abarbeitung innerhalb einer Schleife; die Abarbeitung wird beim ersten Kommando hinter der Schleife fortgesetzt.
#!/bin/csh
#
set line = $<
set input = ( $line )
foreach element ($input)
if ( $element == "otto" ) break
echo $element
end
echo "Jetzt bin ich hinter der Schleife"
Die continue-Anweisung
continue bewirkt den Sprung zum Ende einer Schleife, wobei die Schleife wiederholt durchlaufen wird, solange die Bedingung dafür true ist.
#!/bin/csh
#
set line = $<
set input = ( $line )
foreach element ($input)
if ( $element == "otto" ) continue
echo $element
end
echo "Jetzt bin ich hinter der Schleife"
Die goto-Anweisung
Es wird ein unbedingter Sprung zum bezeichneten Label ausgeführt und mit der Abarbeitung der dahinter folgenden Kommandos begonnen. Das Label muss mit einem Doppelpunkt abgeschlossen am Zeilenanfang stehen.
#!/bin/csh
#
set line = $<
set input = ( $line )
foreach element ($input)
if ( $element == "otto" ) goto ottolabel
echo $element
end
exit
#
ottolabel:
echo "otto geht ins schwimmbad"
exit
Interrupt-Behandlung
Interrupts, die bei der Abarbeitung von shell-Prozeduren auftreten können, können mit der Anweisung onintr abgefangen werden. Dabei gilt folgendes:
onintr label bei erfolgtem Interrupt, Sprung nach label onintr hebt die Interrupt-Behandlung auf onintr - es erfolgt keine Reaktion auf Interrupts
#!/bin/csh
#
onintr error # Interrupt-Behandlung eingeschaltet
set line = $<
set input = ( $line )
onintr # Interrupt-Behandlung ausgeschaltet
set nextinput = $<
foreach element ($input)
echo $element
end
exit
#
error:
echo "Prozedur wurde abgebrochen"
exit
Eingabe von Tastatur
Die interaktive Eingabe über die Tastatur erfolgt mittels der besonderen
Variablen $<.
set varname = $<
Dabei ist zu beachten, dass der eingegebene Text als einzelner kompletter string und nicht als Wortliste interpretiert wird. Soll aus dem eingegebenen Text eine wordlist entstehen, so muss der Inputstring in eine neue Variable übernommen werden. In obigen Prozeduren ist diese Vorgehensweise bereits dokumentiert.
#
set line = $< # Eingabe des Input-strings
set input = ( $line ) # Umwandlung in eine worlist
Grösseres Beispiel eines c-shell-scripts
#!/bin/csh -f
#
# csh - script longlines
# Ausgabe aller Zeilen von files, dessen Laenge einen
# gewaehlten Schwellenwert ueberschreiten
# Usage: longlines [-w width] [file(s)]
set width = 80 # default
if ($#argv > 0) then
if ("$argv[1]" == '-w') then
shift
if ($#argv > 0) then
set a = $argv[1]
if ($a !~ [0-9]* || $a == 0 || $a > 999) then
echo $0\: ungueltige Laenge $a
exit 1
else
set width = $a
shift
endif
else
echo $0\: Laengenangabe fehlt
exit 2
endif
endif
endif
if ($#argv > 0) then
foreach file ($argv[*])
if (-f $file) then
echo $file
awk "length > $width" $file
echo ""
else
echo $0\: kein ASCII-file $file
endif
end
else
awk "length > $width" # standard input
endif
exit 0
Wolfgang Pulina t4879