Nehmen wir an, ich möchte alle .txt -Dateien finden und nach einer Zeichenfolge suchen. Ich würde Folgendes tun:

find ./ -type f -name "*.txt" -exec egrep -iH "something" "{}" \; 

Was ist, wenn ich eine komplexere Filterung wie folgt durchführen möchte:

egrep something file.txt | egrep somethingelse | egrep other 

Inside find -exec? (oder ähnliches)

Bitte denken Sie daran, dass ich nach einer Lösung suche, die ich bei Bedarf einfach eingeben kann. Ich weiß, dass dies mit ein paar Zeilen unter Verwendung eines Shell-Skripts möglich ist, aber das ist nicht das, wonach ich suche.

Antwort

Wenn Sie dies innerhalb von find tun müssen, müssen Sie eine Shell aufrufen:

find ./ -type f -name "*.txt" -exec sh -c "grep -EiH something "$1" | grep -E somethingelse | grep -E other" sh {} \; 

Andere Alternativen umfassen die Verwendung von xargs stattdessen:

find ./ -type f -name "*.txt" | xargs -I{} grep -EiH something {} | grep -EiH somethingelse | grep -EiH other 

Or. En , viel sicherer für beliebige Dateinamen (vorausgesetzt, Ihre find unterstützt -print0):

find ./ -type f -name "*.txt" -print0 | xargs -0 grep -EiH something {} | grep -Ei somethingelse | grep -Ei other 

Oder Sie können stattdessen einfach eine Shell-Schleife verwenden:

find ./ -type f -name "*.txt" -print0 | while IFS= read -d "" file; do grep -Ei something "$file" | grep -Ei somethingelse | grep -Ei other done 

Kommentare

  • Der erste ist genau das, wonach ich gesucht habe. Extrem einfach und klein genug, um je nach meinen Bedürfnissen zu tippen. Danke.
  • … und xargs können auch als xargs -I {} sh -c '...' sh {} verwendet werden, wenn man möchte (es macht Es ist möglich, parallele Jobs mit -P auszuführen, wenn dies gewünscht wird.

Antwort

Bearbeiten: Diese Antwort ist nicht bevorzugt , wird jedoch hier zum Vergleich und zur Veranschaulichung potenziell gefährlicher Fallstricke belassen in Bash-Skripten.


Sie können bash (oder eine andere Shell) als Ihren -exec -Befehl eingeben:

 find -type -f -name "*.txt" -exec bash -c "egrep -iH something "{}" | egrep somethingelse | egrep other" \;  

Einer der Nachteile dieser Vorgehensweise besteht darin, dass mehr erstellt wird Potenzial für verschachtelte Anführungszeichenprobleme, wenn Ihre Befehle komplexer werden. Wenn Sie dies vermeiden möchten, können Sie es in eine for -Schleife aufteilen:

 for i in $(find -type -f -name "*.txt"); do if egrep -iH something "$i" | egrep somethingelse | egrep other; then echo "Found something: $i" fi done  

Kommentare

  • Der erste ist genau das, wonach ich gesucht habe. Extrem einfach und klein genug, um je nach meinen Bedürfnissen zu tippen. Vielen Dank.
  • Diese for -Schleife ist eine sehr schlechte Idee. Auch bekannt als bash pitfall # 1 .
  • Diese "{}" in Ihrem ersten Befehl kann sogar zur Code-Injektion führen. Stellen Sie sich vor, Sie haben Dateien von mir und es gibt ' eine Datei mit dem wörtlichen Namen " & rm -rf ~ & : ".txt. Zum Glück für Sie ist -type -f ungültig, es hat nur Ihr Home-Verzeichnis gespeichert. Beheben Sie den Tippfehler und versuchen Sie es erneut. 🙂 terdon hat es richtig gemacht: find … -exec sh -c '… "$1" …' foo {} \;.
  • Danke für die Information! Ja, die -type -f ist ein Tippfehler, den ich ständig mache, wenn ich find verwende, und ich habe nicht ' merke es nicht in meiner Antwort. Hoppla. Die Antwort von terdon ' ist besser, aber ich ' lasse dies zu Vergleichszwecken.
  • @terdon: tx zum Verweisen auf die Seite mywiki.wooledge.org. ' ist schön, wenn ein paar Allgemeinmediziner an einem Ort zusammengefasst sind.

Schreibe einen Kommentar

Deine E-Mail-Adresse wird nicht veröffentlicht. Erforderliche Felder sind mit * markiert.