Cercare....(grep e egrep)

Una operazione molto utile e' cercare una stringa string in file o cercare una certa cosa nell'output di un comando.

grep

Il piu' semplice comando che si puo'usare e' grep (o egrep), la cui sintassi e' :

grep [options] string file

dove string e' la stringa da cercare e file e' il file nel quale si cerca la stringa.
(N.B. in VMS la sintassi era invertita...).


Per cercare la stringa string in un file, e' sufficiente dare

grep string file

grep cerca esattamente tutti i possibili match di string e li stampa su STDOUT. Se si cerca string ma si cercava STRING, il comando sopra non la trova.
Si puo' allora usare l'opzione -i che cerca string indipendentemente dalle maiuscole-minuscole.

grep -i string file

In generale e' consigliabile dare sempre l'opzione -i.

Se invece si vuole solo sapere quante volte compare string, e' sufficiente dare:

grep -i -c string file


Ovviamente file puo' essere anche l'output di un comando o di un programma, che puo' venire mandato in pipe al grep.
Quindi ad esempio, per cercare un particolare file di cui ci si ricorda solo una parte di nome file_to_find_string, tra tutti i file di una directory, e non si vuole usare find, si puo' fare:

ls -la | grep -i file_to_find_string

oppure, per cercare un particolare processo proc_to_find tra tutti i processi attivi di una macchina, si puo' fare:

ps -edaf [-aux] | grep proc_to_find


Si possono anche cercare stringhe "complicate" usando " " per delimitare la stringa, ad esempio,

grep -i "string1 string2" file

col quale si cerca esattamente "string1 string2".
Ma se si volesse cercare string1 o string2 ?
Si potrebbe usare ancora grep, con altre opzioni, ma esiste un comando piu' adatto...

egrep

Il comando egrep e' simile a grep, ma piu' potente perche' fa uso fa uso delle cosiddette Regular Expressions.

Le Regular Expressions si possono definire come "un modo di descrivere un set di stringhe senza doverle scrivere tutte per esteso" (L. Wall, T. Christiansen, R. Schwartz, Programming Perl)
Ovvero sono uno strumento per descrivere insiemi di caratteri e/o stringhe e per manipolarle. Ma qui e' necessaria una digressione.


Introduzione alle Regular Expression

Considerazioni generali

Regole fondamentali



Omaggio ai gentili partecipanti

Un buon riassunto "tascabile" della sintassi delle R.E. si trova nella guida rapida di Perl, che puo' essere ottenuta al seguente indirizzo (e stampata con una stampante duplex): http://www.mi.infn.it/sem-os-cntc/bigino_perl.ps

Ecco un breve estratto, con indicate le parti specifiche a Perl:


Quanto sono "standard" le R.E.?

La serie di caratteri descritte in questo documento si applica sostanzialmente a tutte le applicazioni di uso comune: egrep, perl, python, le librerie POSIX distribuite con i compilatori C/C++, vi (dopo aver dato il comando set extended), eccetera.
Per le funzioni piu' avanzate la realta' si presenta piu' complicata:


Per approfondire l'argomento R.E.

Jeffrey E.F. Friedl, "Mastering Regular Expressions", O'Reilly, 1997.


Con quanto appena descritto, tornando all'uso pratico di egrep, e' quindi possibile fare delle ricerche piu' selettive.
Volendo cercare in un file string1 o string2, si puo' fare:

egrep -i '(string1|string2)' file

egrep e' particolarmente utile per ricerche complesse di particolari stringhe: linee di commento o include in un programma, date in un log file, ecc.

Se, ad esempio, vogliamo tutte le righe di un programmma in Fortran che non sono di commento, bastera' dare:

egrep -i '^[^c] program.f

Se invece vogliamo vedere che include locali e non di sistema ha un programma c, possiamo fare:

egrep -i '^#include[ ]+"' program.c


Ecco alcuni esempi di egrep utili (o curiosi..):

I seguenti due esempi cercano in ogni file di tipo *.pl in una certa directory, la stringa contenente il path a Perl.
Danno esattamente lo stesso output...

egrep '[Pp]erl[0-9]' *.pl

egrep '^#\!([a-z]|/)+(P|p)erl[0-9]' *.pl

ecco un esempio piu' complesso di pipe con egrep

ls -latr *.his | egrep -i 'k+[a-z]+_dp'

questo comando ordina in senso temporale, dal piu' vecchio al piu' nuovo',file con estensione .his nel cui nome ci sia almeno un k seguito da almeno un'altra lettera seguita da _dp.