
Ich möchte mit grep ein Verzeichnis rekursiv durchsuchen, indem ich in einer Datei aufgelistete Muster verwende, und dann jedes Ergebnis zur späteren Bezugnahme in einer eigenen Datei speichern.
Ich habe einen Versuch gemacht (mitdiese Frageals Leitfaden) und kam zu folgendem Ergebnis:
#!/bin/bash
mkdir -p grep_results # For storing results
echo "Performing grep searches.."
while IFS='' read -r line || [[ -n "$line" ]]; do
echo "Seaching for $line.."
grep -r "$line" --exclude-dir=grep_results . > ./grep_results/"$line"_infile.txt
done
echo "Done."
Wenn ich es jedoch ausführe, bleibt die Konsole hängen, bis ich STRG-C drücke:
$ bash grep_search.sh search_terms.txt
Performing grep searches..
Wo liegt das Problem mit diesem Skript? Oder gehe ich falsch vor?
Antwort1
Hier gibt es einige Probleme:
Die
while
Schleife liest keine Eingabe. Das richtige Format istwhile read line; do ... ; done < input file
Oder
some other command | while read ...
Ihre Schleife hängt daher und wartet auf Eingaben. Sie können dies testen, indem Sie Ihr Skript ausführen, dann etwas eingeben und die Eingabetaste drücken (hier habe ich eingegeben
foo
):$ foo.sh Performing grep searches.. foo Searching for foo..
Sie können dies verbessern, indem Sie Ihrem Folgendes eine Eingabeaufforderung hinzufügen
read
:while IFS='' read -p "Enter a search pattern: " -r line ...
Dies wird jedoch weiterhin ausgeführt, bis Sie es mit Ctrl+ stoppen C.
Das
|| [[ -n "$line" ]]
(was bedeutet „ODER die Variable $line ist nicht leer“) wird nie ausgeführt. Da es hängt, wird das „ODER“ nie erreicht. Ich verstehe sowieso nicht, was Sie damit machen wollten. Wenn Sie nach „wenn definiert“ suchen und „wenn nicht“ verwendenread
möchten , benötigen Sie etwas wie:$line
$line
read
if [[ -n "$line" ]]; then grep -r "$line" --exclude-dir=grep_results > ./grep_results/"$line"_infile.txt else while IFS='' read -p "Enter a search pattern: " -r line || [[ -n "$line" ]]; do grep -r "$line" --exclude-dir=grep_results > ./grep_results/"$line"_infile.txt done fi
Wenn hier
$line
nicht definiert ist, müssen Sie es trotzdem manuell eingeben. Ein saubererer Ansatz wäre, entweder eine Datei in diewhile
Schleife einzuspeisen:while IFS='' read -r line || [[ -n "$line" ]]; do grep -r "$line" --exclude-dir=grep_results > ./grep_results/"$line"_infile.txt done < list_of_patterns.txt