Trovare file che contengono una determinata stringa usando find (1) e grep (1)


70

find . -type f -print -exec cat {} \; | grep some string

Il comando sopra non stampa il percorso del file.

Sto utilizzando: Ubuntu, bash 4.


Forse non soddisfa i risultati previsti a causa del filtro grep. Che dire di questo:find . -type f -fprint /dev/stderr -exec cat {} \; | grep some string
artistoex,

Qual è l'obiettivo che vuoi raggiungere? All'uscita stai ricevendo stringhe grepped dai file, vuoi il percorso di quei file?
mirkobrankovic,

Sì, desidero stampare il percorso dei file che contengono la stringa "una stringa". Il suggerimento @artistoex stampa tutti i percorsi dei file.
H.Rabiee,

Potresti semplicemente voler usare ackgrep attraverso tutti i file nella directory corrente, eventualmente filtrando solo su alcuni tipi di file.
Jaap Eldering,

Risposte:


87

Questo perché stai alimentando grepun flusso di testo che contiene solo nomi di file. Dato che non hai fornito nomi di file come argomenti per grep, non ci si può aspettare di dedurre da quale file provenga una linea corrispondente. Utilizzare xargs:

find . -type f -print | xargs grep "some string"

Dato che hai GNU find / xargs, questo è un modo più sicuro per xargs di leggere i nomi dei file:

find . -type f -print0 | xargs -0 grep "some string"

Se vuoi solo i nomi di file che hanno una linea corrispondente senza mostrare la linea corrispondente:

find . -type f -print0 | xargs -0 grep -l "some string"

Come unirei i comandi sopra con ricerca e sostituzione? Come in, grep quindi sed?
CMCDragonkai,

1
la pipeline find | grep genera nomi di file, quindi:sed '...' $(find ... | xargs grep -l ...)
glenn jackman,

107

Io uso

grep "some string" . -R

e funziona più velocemente

ps

Caso d'uso più complesso

grep -HiRE "some string|other string" . #H for file printing, i for case-insensitive, R for recursive search, E for regex 

Per leggere la spiegazione dei parametri

grep --help | grep -- -i

17
E -nse vuoi i numeri di riga. +1 per una risposta semplificata.
Chad Skeeters,

@ChadSkeeters esattamente. L'uso della ricerca non fornisce tale soluzione.
ArcherGodson

1
Questa dovrebbe essere contrassegnata come la risposta corretta, per essere onesti. Quello attualmente selezionato dettaglia qualcos'altro completamente.

12

Cerco spesso il codice sorgente in strutture di cartelle complesse e trovo utile utilizzando:

cd /your/folder/
grep -rHino "your string"

Con questi parametri, senza usare find , ottengo il percorso completo del file e il numero di riga che contiene la stringa specificata .

È anche facile da ricordare perché BASH è attraverso la tua ricerca come un rHino :)

Mostrerò come funziona con un rapido esempio.

Mostriamo il contenuto di un file usando cat:

jeeves ~ # cat fw.stop
#!/bin/sh
echo "Stopping firewall and allowing everyone..."
iptables -F
iptables -X
iptables -t nat -F
iptables -t nat -X
iptables -t mangle -F
iptables -t mangle -X
iptables -P INPUT ACCEPT
iptables -P FORWARD ACCEPT
iptables -P OUTPUT ACCEPT

E cerchiamo ricorsivamente tutti i file contenenti la stringa "iptables -P":

jeeves ~ # grep -rinHo "iptables -P"
fw.stop:9:iptables -P
fw.stop:10:iptables -P
fw.stop:11:iptables -P

Come puoi vedere nell'output, abbiamo nomefile: hit row: stringa cercata

Ecco una descrizione più dettagliata dei parametri utilizzati:

-r Per ogni operando di directory, leggere ed elaborare tutti i file in quella directory, in modo ricorsivo. Segui i collegamenti simbolici sulla riga di comando, ma salta i collegamenti simbolici che si incontrano in modo ricorsivo. Si noti che se non viene fornito alcun operando di file, grep cerca la directory di lavoro. È uguale all'opzione '--directories = recurse'.

-i Stampa il nome del file per ogni corrispondenza. Questo è il valore predefinito quando c'è più di un file da cercare.

-n Prefisso ogni riga di output con il numero di riga basato su 1 all'interno del suo file di input. (-n è specificato da POSIX.)

-H Stampa il nome del file per ogni corrispondenza. Questo è il valore predefinito quando c'è più di un file da cercare.

-o Stampa solo le parti corrispondenti (non vuote) delle linee corrispondenti, con ciascuna di tali parti su una linea di output separata. Le linee di output usano gli stessi delimitatori dell'input e i delimitatori sono byte nulli se viene utilizzato anche -z (--null-data) (vedere Altre opzioni).


2

ho preferito

| trova il file | make grep non trova il file | mostra il percorso completo del file

find / -type f -exec grep 'some string' {} \; -exec echo {} \;


0

Silver Searcher è un programma di utilità molto veloce e pratico per cercare file e contenuti.

Per risolvere il tuo problema, il comando Silver Searcher sarebbe simile a questo ...

ag 'some string' -l

-l Stampa solo nomi di file che contengono corrispondenze (non stampare le righe corrispondenti)

Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.