Nie jestem pewny:
grep -r -i 'the brown dog' /*
to naprawdę to, co miałeś na myśli. Oznaczałoby to rekurencyjnie grep we wszystkich nie ukrytych plikach i katalogach w /(ale nadal zaglądanie do ukrytych plików i katalogów wewnątrz nich).
Zakładając, że miałeś na myśli:
grep -r -i 'the brown dog' /
Kilka rzeczy do zapamiętania:
- Nie wszystkie
grepimplementacje obsługują -r. A wśród tych, które się tak zachowują, zachowania się różnią: niektóre podążają za dowiązaniami symbolicznymi do katalogów podczas przechodzenia przez drzewo katalogów (co oznacza, że możesz skończyć przeglądać kilka razy w tym samym pliku lub nawet działać w nieskończonych pętlach), niektóre nie. Niektóre zaglądają do plików urządzeń ( /dev/zerona przykład zajmie to trochę czasu ) lub potoków lub plików binarnych ... niektóre nie.
- Jest skuteczny, ponieważ
grepzaczyna przeszukiwać pliki, gdy tylko je odkryje. Ale gdy szuka w pliku, nie szuka już więcej plików do przeszukania (co w większości przypadków jest prawdopodobnie równie dobre)
Twój:
find / -type f -exec grep -i 'the brown dog' {} \;
(usunięto to, -rco nie miało sensu tutaj) jest strasznie nieefektywne, ponieważ uruchamiasz jeden grepna plik. ;powinien być używany tylko dla poleceń, które akceptują tylko jeden argument. Ponadto tutaj, ponieważ grepwygląda tylko w jednym pliku, nie wydrukuje nazwy pliku, więc nie będziesz wiedział, gdzie są dopasowania.
Nie przeglądasz plików urządzeń, potoków, dowiązań symbolicznych ..., nie podążasz za dowiązaniami symbolicznymi, ale nadal potencjalnie zaglądasz do takich rzeczy jak /proc/mem.
find / -type f -exec grep -i 'the brown dog' {} +
byłoby znacznie lepiej, ponieważ grepuruchomiono by jak najmniej poleceń. Otrzymasz nazwę pliku, chyba że ostatnie uruchomienie zawiera tylko jeden plik. W tym celu lepiej użyć:
find / -type f -exec grep -i 'the brown dog' /dev/null {} +
lub z GNU grep:
find / -type f -exec grep -Hi 'the brown dog' {} +
Pamiętaj, że grepnie zostanie uruchomiony, dopóki findnie znajdzie wystarczającej liczby plików do przeżuwania, więc wystąpi pewne początkowe opóźnienie. I findnie będzie kontynuował wyszukiwania kolejnych plików, dopóki poprzednie grepnie powróci. Przydzielanie i przekazywanie dużej listy plików ma pewien (prawdopodobnie nieistotny) wpływ, więc w sumie prawdopodobnie będzie mniej wydajne niż to, grep -rże nie podąża za dowiązaniem symbolicznym ani nie przegląda urządzeń.
Za pomocą narzędzi GNU:
find / -type f -print0 | xargs -r0 grep -Hi 'the brown dog'
Jak wyżej, grepuruchomionych findzostanie jak najmniej instancji, ale będzie ona nadal szukała więcej plików, podczas gdy pierwsze grepwywołanie zajrzy do pierwszej partii. To może, ale nie musi być zaletą. Na przykład dane przechowywane na obrotowych dyskach twardych findi grepuzyskiwanie dostępu do danych przechowywanych w różnych miejscach na dysku spowolnią przepustowość dysku, powodując ciągłe ruchy głowicy dysku. W konfiguracji RAID (gdzie findi grepmoże uzyskiwać dostęp do różnych dysków) lub na dyskach SSD może to mieć pozytywny wpływ.
W konfiguracji RAID, bieganie kilka jednoczesnych grep wywołania może również poprawić rzeczy. Nadal z narzędziami GNU na macierzy RAID1 z 3 dyskami,
find / -type f -print0 | xargs -r0 -P2 grep -Hi 'the brown dog'
może znacznie zwiększyć wydajność. Zauważ jednak, że drugi grepzostanie uruchomiony dopiero po znalezieniu wystarczającej liczby plików do wypełnienia pierwszego greppolecenia. Możesz dodać -nopcję xargs, aby stało się to wcześniej (i przekazać mniej plików na jedno grepwywołanie).
Zauważ też, że jeśli przekierowujesz xargsdane wyjściowe na cokolwiek innego niż urządzenie końcowe, grepss zacznie buforować swoje dane wyjściowe, co oznacza, że dane wyjściowe tych grepprawdopodobnie zostaną nieprawidłowo przeplecione. Będziesz musiał użyć na nich stdbuf -oL(jeśli jest dostępny, jak na GNU lub FreeBSD), aby obejść ten problem (nadal możesz mieć problemy z bardzo długimi liniami (zazwyczaj> 4KiB)) lub poproś każde z nich o zapisanie ich wyników w osobnym pliku i połączenie ich. wszystko w końcu.
Tutaj ciąg, którego szukasz, jest naprawiony (nie jest wyrażeniem regularnym), więc użycie tej -Fopcji może mieć znaczenie (mało prawdopodobne, ponieważ grepimplementacje wiedzą, jak to zoptymalizować).
Inną rzeczą, która może mieć dużą różnicę, jest ustawienie języka na C, jeśli jesteś w ustawieniu wielobajtowym:
find / -type f -print0 | LC_ALL=C xargs -r0 -P2 grep -Hi 'the brown dog'
Aby uniknąć zaglądania do wnętrza /proc, /sys... użyj -xdevi określ systemy plików, w których chcesz wyszukiwać:
LC_ALL=C find / /home -xdev -type f -exec grep -i 'the brown dog' /dev/null {} +
Lub przycinaj ścieżki, które chcesz jawnie wykluczyć:
LC_ALL=C find / \( -path /dev -o -path /proc -o -path /sys \) -prune -o \
-type f -exec grep -i 'the brown dog' /dev/null {} +