[KURS] Programowanie w powłoce #5: strumienie, potoki i filtry

Nadszedł czas na kolejną część kursu Programowanie w powłoce. Dzisiaj przedstawię podstawowe informacje dotyczące strumieni, potoków oraz filtrów.

Strumienie

Procesy w systemie korzystają z trzech strumieni:

  • stdin – standardowe wejście (deskryptor 0) – przeważnie jest to klawiatura komputera.
  • stdout – standardowe wyjście (deskryptor 1) – przeważnie jest to monitor komputera,
  • stderr – standardowe wyjście błędów (deskryptor 2) – przeważnie jest to monitor komputera.

Do przekierowania używa się znaku > poprzedzonego odpowiednim deskryptorem np.:

szmitas@szmitas-ubuntu:~$ cat plik_ktorego_nie_ma.txt 2> bledy.txt
szmitas@szmitas-ubuntu:~$ cat bledy.txt
cat: plik_ktorego_nie_ma.txt: No such file or directory

Krótka analiza: poleceniem cat próbuję wyświetlić zawartość pliku, który nie istnieje – czyli wystąpi błąd, który zostaje wyłapany (2>) i przekierowany do pliku tekstowego o nazwie bledy.txt.
Inny przykład:

szmitas@szmitas-ubuntu:~/Pulpit/pliki$ ls > lista.txt
szmitas@szmitas-ubuntu:~/Pulpit/pliki$ cat lista.txt
aMule
bieganie
filmy
gry
inne
lista.txt
programowanie
programy
sterowniki
wygląd
zdjęcia

Rezultat polecenia ls przekierowuję do pliku tekstowego (>).

Uwaga! Operator > powoduje nadpisanie pliku tekstowego. Aby dopisać informację do jego końca zastosuj >>.

Podsumowanie:

  • polecenie 2> plik – powoduje wysłanie stderr do pliku o nazwie plik.
  • polecenie < plik – powoduje odczyt stdin z pliku o nazwie plik.
  • polecenie 2>> plik – powoduje dopisanie stderr do pliku o nazwie plik.
  • polecenie <<r plik – powoduje odczyt stdin z pliku, aż do znaku „r”.

Potoki

Potoki pozwalają na przesyłanie danych wyjściowych jednego polecenia, na wejście drugiego. Polecenia łączy się za pomocą operatora | zwanego „rurą” (ang. pipe).
Przykład:

polecenie1 | polecenie2

Wyjście (stdout) polecenia pierwszego zostanie przekazane na wejście (stdin) polecenia drugiego. Oczywiście potoki mogą być wielopoziomowe:

polecenie1 | polecenie2 | polecenie3 | polecenie4

Praktyczny przykład:

szmitas@szmitas-ubuntu:~$ ls | wc -l
22

Wyjście polecenia ls (wypisanie listy plików/katalogów) zostaje przekazane poleceniu wc -l (zliczającemu liczbę linii) – rezultat 22.

A teraz ulubione zadanko mojego wykładowcy:
Pytanie: Jaki będzie wynik?

tail -n 10 czytaj.to | head -n 10 | tail -n 3 | wc - w

Odpowiedź pozostawiam każdemu z was. Konkretna zawartość pliku nie jest istotna (zakładamy jedynie, że istnieje) – liczy się tok myślenia :)

Filtry

Filtry są poleceniami modyfikującymi w określony sposób informację wejściową i przekazującymi ją na wyjście. Filtr pobiera zawsze dane ze standardowego wejścia (stdin) i przesyła wyniki na standardowe wyjście (stdout). Można je więc łączyć z potokami np.

cat ~/.xsession-errors | more

Filtr more sprawia, że na ekranie zostanie wyświetlone tyle linii tekstu ile zmieści się na ekranie (tekst zostanie podzielony na strony).

Inne filtry:

  • more,
  • less,
  • sort,
  • grep.
Jeżeli powyższy artykuł nie rozwiązał lub rozwiązał częściowo Twój problem, dodaj swój komentarz opisujący, w którym miejscu napotkałeś trudności.
Mile widziane komentarze z uwagami lub informacjami o rozwiązaniu problemu.
  • http://kwpolska.co.cc Kwpolska

    Filtry? Rury (pipe). Pipe’ować można wszystko. Przyklad:

    echo 'get plik' | sftp serwer.com

    spowoduje połączenie się po SSH do serwer.com i pobranie pliku plik.
    Kolejny przykład:

    echo '/etc/rc.d/httpd stop' | ssh root@serwer.com

    spowoduje zalogowanie się na roota po ssh, wykonanie komendy /etc/rc.d/httpd stop i wylogowanie się.

    P.S. na tym blogu, w tych komentarzach, semantyka LEŻY. pre, nie blockquote.

    • Szmitas

      Nieuważnie przeczytałeś wpis. Filtry to filtry (przykład pokazuje zastosowanie filtru more a nie potoku | ), a potoki to rury, błędu nie popełniłem.