BASH

Instrukcja warunkowa

  • 2006-12-24 14:44
  • 0 komentarzy
  • 7005 odsłon
  • Oceń ten tekst jako pierwszy

Instrukcja warunkowa


Jak w każdym języku programowania muszą istnieć instrukcje warunkowe. Jak wiadomo służą one do sprawdzania warunków i odpowiedniego reagowania na spełnione i/lub niespełnione warunki. Składnia jest prosta jednak na początku może się mylić osobom piszącym w delphi/pascalu.

if warunek
then
  polecenia
fi


Ważne jest aby then było w nowej linii a nie w jednej razem z if. Słowem kończącym blok wykonywany jest fi. Jeśli ktoś koniecznie chce używać if i then w jednej linii to można to zrobić tak:

if warunek ; then
  polecenia
fi


Ten średnik po warunku jest bardzo istotny. Oznacza to, że warunek się już skonczył i wszystko po nim jest tak jak by w nowej linii. Nie dotyczy to tylko instrukcji if ale w każdym miejscu w skrypcie jak napiszemy dwa polecenia po sobie w jednej linii i oddzielimy je średnikiem to bedą wykonane tak jak by były napisane jedno pod drugim.

#!/bin/sh
echo "aaa" ; echo "sss"


Powyższy skrypt wykona się tak samo jak:

#!/bin/sh
echo "aaa"
echo "sss"


Myślę, że dość jasno zostało to wyjasnione. Jak to bywa najczęściem razem z instrukcja if jest także instrukcja else.

if warunek
then
  polecenie
else
  inne_polecenie
fi


Czasami bywa nam potrzebne także użyć połączenia if i else. Z takiego połączenia wychodzi elif.

if warunek
then
  polecenie
elif warunek
then
  inne_polecenie
else
  jeszcze_inne_polecenie
fi


Instrukcja jest dość intuicyjna i chyba nie trzeba za wiele tłumaczyć. Praktyczne wykorzystanie instrukcji if może być następujące. Sprawdzimy czy działa nam internet takim bardzo prostym skryptem:

#!/bin/sh
zm=`ping -c 1 google.pl | grep "100% packet loss"`
if [[ `echo $zm` == "" ]]
then
  echo "Mamy internet"
else
  echo "Inetrnetu brak"
fi


Zapewne zagadka jest dla ciebie druga linia skryptu. Może wyglądać to dość skomplikowanie ale ogólna zasada jest bardzo prosta. Całą tą linie można podzielić na jakieś trzy części:

zm=` | `
ping -c 1 google.pl
grep "100% packet loss"


Pierwsze z poleceń wydaje się proste jednak pewną zagadką może być pionowa kreska. Jest to pipe zwany także potokiem lub rurka. Jeśli masz poprawny nadruk na klawiaturze lub odpowiednia czcionka zostanie wybrana do wyświetlenia znaku to powinny to być dwie kreseczki pionowe jedna nad drugą z małą przerwą pomiędzy nimi, i właśnie to jest ta rurka. Jeśli kilka programów napiszemy w jednej linii oddzielając je od siebie pionową kreską to są one wykonywane od lewej do prawej i to co zwroci jeden program jest wysyłane do następnego w kolejce. Druga część naszej omawianej linii dotyczy pingowania google. Zakładamy, że jeśli ping wróci od google to znak ze działa nam internet. Nasz program w conajmniej dwóch przypadkach może zwracać falszywą informacje.
1.Gdy nasz skrypt zostanie uruchomiony na serwerze google.pl wtedy ping będzie lokalny i nie musi to oznaczać ze internet działa
2.Gdy serwer obsługujący google.pl przestanie działać i nie wróci do niego ping
Oba przypadki są na tyle mało prawodopodobne, że można założyć, że skrypt działa poprawnie i drukuje prawdziwą informacje. Parametr -c 1 w poleceniu ping oznacza, że wysyłamy tylko jeden pakiet pingujący (normalnie ping działa, aż nie nacisniemy ctrl+c). To co zwróci ping wysyłamy do programu grep, który z podanej zmiennej wyłuskuje podany jako parametr tekst. W naszym wypadku ma znaleźć ?100% packet loss?. Wysyłamy tylko jeden pakiet więc są tylko dwa przypadki do rozpatrzenia, albo ping wroci albo nie. Gdy ping wróci grep nie będzie mógł znaleźć szukanego ciągu znaków bo go po prostu nie będzie i zmienna zm nic nie będzie zawierać. Jeśli ping nie wróci grep znajdzie szukany tekst i ten szukany tekst zostanie przekazany do zmiennej zm. Właściwie to najtrudniejsza część analizy skryptu za nami. Teraz zostało tylko sprawdzić co jest w zmiennej zm, jeśli jest ona pusta to oznacza, że internet działa. Jeśli jest w niej coś to na pewno jest to ?100% packet loss? czyli to co zwrócił grep.

A co gdy chcemy porównać liczby która jest wieksza a która mniejsza? W BASHu znaki < nie służą do porównywania wartości liczb ponieważ służą do strumieni o których będzie pozniej. Nie oznacza to, że nie możemy jako zadanie dać naszemy skryptowi sprawdzenie która z liczb jest wieksza, 7 czy 3. Poniższy skrypt pokazuje jak to zrobić

#!/bin/sh
if [ 7 -gt 3 ]
then
  echo "7 wieksze"
else
  echo "3 wieksze"
fi


Oczywiście znakiem > zasąpiono -gt. W działaniu nie ma żadnej filozofii tylko trzeba pamiętać, który znak czemu odpowiada. Poniżej napisane są wszystkie znaki porównania i ich odpowiedniki których należy używać w skryptach:
  • Dla > używamy -gt
  • Dla < używamy -lt
  • Dla >= używamy -ge
  • Dla <= używamy -le

Jak można było zauważyć w przykładzie sprawdzającym czy działa nam internet użyłem znaków == jako porównania. Jeśli chcielibyśmy użyć różne to wystarczy napisasc != tak samo jak w C.

Bardzo ciekawym i użytecznym poleceniem przy instrukcjach warunkowych jest test. Może być wykorzystywany do porównywania łańcuchów, plików i liczb. Ma także możliwość sprawdzania czy dany plik istnieje i jakie posiada atrybuty. Najczęściej zamiast pisac w porównaniu słowo test używa się podwójnych nawiasów kwadratowych, np.

#!/bin/bash
 
if [[ -w jakis_plik ]]
then
  echo "jakis_plik jest do zapisu"
else
  echo "jakis_plik nie jest do zapisu"
fi


Powyższy skrypt sprawdza czy jest możliwość zapisu do danego pliku. Tych przełączników jest sporo i można więcej się o nich dowiedziec z manuala programu test jednak ja najbardziej użyteczne wypisałem poniżej:

  • -e - Plik istnieje
  • -r - Plik jest do oczytu
  • -x - Plik jest wykonywalny
  • -w - Jest możliwość zapisu do pliku
  • -d - Plik istnieje i jest katalogiem
  • -L lub -h - Plik istnieje i jest linkiem symbolicznym