
grep
command je zkratka pro „global regular expression print“ a je to jeden z nejvýkonnějších a běžně používaných příkazů v Linuxu.
grep
hledá v jednom nebo více vstupních souborech řádky, které odpovídají danému vzoru, a zapisuje každý odpovídající řádek na standardní výstup. Pokud nejsou zadány žádné soubory, grep
čte ze standardního vstupu, což je obvykle výstup jiného příkazu.
V tomto článku vám ukážeme, jak používat grep
pomocí praktických příkladů a podrobných vysvětlení nejběžnějších GNU grep
možnosti.
grep
Syntaxe příkazu #
Syntaxe pro grep
příkaz je následující:
grep [OPTIONS] PATTERN [FILE...]
Položky v hranatých závorkách jsou volitelné.
OPTIONS
- Nula nebo více možností. Grep obsahuje řadu možností, které řídí jeho chování.PATTERN
- Vzor vyhledávání.FILE
- Žádný nebo více názvů vstupních souborů.
Aby bylo možné v souboru vyhledávat, uživatel spouštějící příkaz musí mít k souboru přístup pro čtení.
Vyhledat řetězec v souborech #
Nejzákladnější použití grep
příkaz je vyhledat řetězec (text) v souboru.
Chcete-li například zobrazit všechny řádky obsahující řetězec bash
z /etc/passwd
soubor, spustíte následující příkaz:
grep bash /etc/passwd
Výstup by měl vypadat nějak takto:
root:x:0:0:root:/root:/bin/bash
linuxize:x:1000:1000:linuxize:/home/linuxize:/bin/bash
Pokud řetězec obsahuje mezery, musíte jej uzavřít do jednoduchých nebo dvojitých uvozovek:
grep "Gnome Display Manager" /etc/passwd
Invertovat shodu (vyloučit) #
Chcete-li zobrazit řádky, které neodpovídají vzoru, použijte -v
(nebo --invert-match
).
Chcete-li například vytisknout řádky, které neobsahují řetězec nologin
byste použili:
grep -v nologin /etc/passwd
root:x:0:0:root:/root:/bin/bash
colord:x:124:124::/var/lib/colord:/bin/false
git:x:994:994:git daemon user:/:/usr/bin/git-shell
linuxize:x:1000:1000:linuxize:/home/linuxize:/bin/bash
Použití Grepu k filtrování výstupu příkazu #
Výstup příkazu lze filtrovat pomocí grep
potrubím a na terminálu budou vytištěny pouze čáry odpovídající danému vzoru.
Chcete-li například zjistit, které procesy běží ve vašem systému jako uživatel www-data
můžete použít následující ps
příkaz:
ps -ef | grep www-data
www-data 18247 12675 4 16:00 ? 00:00:00 php-fpm: pool www
root 18272 17714 0 16:00 pts/0 00:00:00 grep --color=auto --exclude-dir=.bzr --exclude-dir=CVS --exclude-dir=.git --exclude-dir=.hg --exclude-dir=.svn www-data
www-data 31147 12770 0 Oct22 ? 00:05:51 nginx: worker process
www-data 31148 12770 0 Oct22 ? 00:00:00 nginx: cache manager process
Na příkaz můžete také zřetězit více kanálů. Jak můžete vidět ve výstupu výše, je zde také řádek obsahující grep
proces. Pokud nechcete, aby se tento řádek zobrazoval, předejte výstup jinému grep
instance, jak je uvedeno níže.
ps -ef | grep www-data | grep -v grep
www-data 18247 12675 4 16:00 ? 00:00:00 php-fpm: pool www
www-data 31147 12770 0 Oct22 ? 00:05:51 nginx: worker process
www-data 31148 12770 0 Oct22 ? 00:00:00 nginx: cache manager process
Rekurzivní vyhledávání #
Chcete-li rekurzivně hledat vzor, vyvolejte grep
pomocí -r
možnost (nebo --recursive
). Při použití této možnosti grep
prohledá všechny soubory v zadaném adresáři a přeskočí symbolické odkazy, které se vyskytují rekurzivně.
Chcete-li sledovat všechny symbolické odkazy, namísto -r
, použijte -R
možnost (nebo --dereference-recursive
).
Zde je příklad ukazující, jak hledat řetězec linuxize.com
ve všech souborech v /etc
adresář:
grep -r linuxize.com /etc
Výstup bude obsahovat odpovídající řádky s předponou úplnou cestou k souboru:
/etc/hosts:127.0.0.1 node2.linuxize.com
/etc/nginx/sites-available/linuxize.com: server_name linuxize.com www.linuxize.com;
Pokud použijete -R
možnost, grep
bude následovat všechny symbolické odkazy:
grep -R linuxize.com /etc
Všimněte si posledního řádku výstupu níže. Tento řádek se nevytiskne, když grep
se vyvolá pomocí -r
protože soubory uvnitř Nginx sites-enabled
adresář jsou symbolické odkazy na konfigurační soubory v sites-available
adresář.
/etc/hosts:127.0.0.1 node2.linuxize.com
/etc/nginx/sites-available/linuxize.com: server_name linuxize.com www.linuxize.com;
/etc/nginx/sites-enabled/linuxize.com: server_name linuxize.com www.linuxize.com;
Zobrazit pouze název souboru #
Chcete-li potlačit výchozí grep
výstup a tisk pouze názvy souborů obsahujících odpovídající vzor, použijte -l
(nebo --files-with-matches
).
Níže uvedený příkaz prohledá všechny soubory končící na .conf
v aktuálním pracovním adresáři a vytiskne pouze názvy souborů obsahujících řetězec linuxize.com
:
grep -l linuxize.com *.conf
Výstup bude vypadat nějak takto:
tmux.conf
haproxy.conf
-l
volba se obvykle používá v kombinaci s rekurzivní volbou -R
:
grep -Rl linuxize.com /tmp
Vyhledávání bez rozlišení malých a velkých písmen #
Ve výchozím nastavení grep
rozlišuje velká a malá písmena. To znamená, že velká a malá písmena jsou považována za odlišná.
Chcete-li při vyhledávání ignorovat malá a velká písmena, vyvolejte grep
pomocí -i
možnost (nebo --ignore-case
).
Například při hledání Zebra
bez jakékoli možnosti následující příkaz nezobrazí žádný výstup, tj. existují odpovídající řádky:
grep Zebra /usr/share/words
Ale pokud provedete vyhledávání bez rozlišení malých a velkých písmen pomocí -i
možnost, bude odpovídat velkým i malým písmenům:
grep -i Zebra /usr/share/words
Zadáním „Zebra“ bude odpovídat „zebra“, „ZEbrA“ nebo jakékoli jiné kombinaci velkých a malých písmen pro daný řetězec.
zebra
zebra's
zebras
Vyhledat celá slova #
Při hledání řetězce grep
zobrazí všechny řádky, kde je řetězec vložen do větších řetězců.
Pokud například hledáte „gnu“, budou se shodovat všechny řádky, kde je „gnu“ vloženo do větších slov, jako je „cygnus“ nebo „magnum“:
grep gnu /usr/share/words
cygnus
gnu
interregnum
lgnu9d
lignum
magnum
magnuson
sphagnum
wingnut
Chcete-li vrátit pouze ty řádky, kde je zadaný řetězec celé slovo (uzavřené neslovnými znaky), použijte -w
(nebo --word-regexp
).
a-z
, A-Z
a 0-9
) a podtržítka (_
). Všechny ostatní znaky jsou považovány za neslovní znaky.
Pokud spustíte stejný příkaz jako výše, včetně -w
možnost grep
příkaz vrátí pouze ty řádky, kde je gnu
je zahrnuto jako samostatné slovo.
grep -w gnu /usr/share/words
gnu
Zobrazit čísla řádků #
-n
(nebo --line-number
) říká grep
pro zobrazení čísla řádků obsahujících řetězec, který odpovídá vzoru. Když je použita tato možnost, grep
vytiskne shody na standardní výstup s předponou s číslem řádku.
Například pro zobrazení řádků z /etc/services
soubor obsahující řetězec bash
s předponou odpovídající číslo řádku, můžete použít následující příkaz:
grep -n 10000 /etc/services
Níže uvedený výstup nám ukazuje, že shody byly nalezeny na řádcích 10423 a 10424.
10423:ndmp 10000/tcp
10424:ndmp 10000/udp
Počet shod #
Chcete-li vytisknout počet odpovídajících řádků na standardní výstup, použijte -c
(nebo --count
).
V níže uvedeném příkladu počítáme počet účtů, které mají /usr/bin/zsh
jako skořápka.
regular expression
grep -c '/usr/bin/zsh' /etc/passwd
4
Tichý režim #
-q
(nebo --quiet
) říká grep
běžet v tichém režimu, aby se na standardním výstupu nic nezobrazovalo. Pokud je nalezena shoda, příkaz se ukončí se stavem 0
. To je užitečné při použití grep
ve skriptech shellu, kde chcete zkontrolovat, zda soubor obsahuje řetězec, a provést určitou akci v závislosti na výsledku.
Zde je příklad použití grep
v tichém režimu jako testovací příkaz v if
prohlášení:
if grep -q PATTERN filename
then
echo pattern found
else
echo pattern not found
fi
Základní regulární výraz #
GNU Grep má tři sady funkcí regulárních výrazů, Basic, Extended a Perl-kompatibilní.
Ve výchozím nastavení grep
interpretuje vzor jako základní regulární výraz, kde všechny znaky kromě metaznaků jsou ve skutečnosti regulární výrazy, které si odpovídají.
Níže je uveden seznam nejčastěji používaných metaznaků:
-
Použijte
^
(stříška), aby odpovídal výrazu na začátku řádku. V následujícím příkladu řetězeckangaroo
se bude shodovat pouze v případě, že se vyskytuje na samém začátku řádku.grep "^kangaroo" file.txt
-
Použijte
$
(dolar), aby odpovídal výrazu na konci řádku. V následujícím příkladu řetězeckangaroo
se bude shodovat pouze v případě, že se objeví na samém konci řádku.grep "kangaroo$" file.txt
-
Použijte
.
(tečka), aby odpovídal libovolnému jednotlivému znaku. Chcete-li například odpovídat všemu, co začínákan
pak má dva znaky a končí řetězcemroo
, můžete použít následující vzor:grep "kan..roo" file.txt
-
Použijte
[ ]
(závorky), aby odpovídaly libovolnému jednotlivému znaku uzavřenému v závorkách. Najděte například řádky, které obsahujíaccept
nebo „accent
, můžete použít následující vzor:grep "acce[np]t" file.txt
-
Použijte
[^ ]
aby odpovídal libovolnému jednotlivému znaku, který není uzavřen v závorkách. Následující vzor bude odpovídat jakékoli kombinaci řetězců obsahujícíchco(any_letter_except_l)a
, napříkladcoca
,cobalt
a tak dále, ale nebude odpovídat řádkům obsahujícímcola
,grep "co[^l]a" file.txt
Chcete-li uniknout speciálnímu významu dalšího znaku, použijte \
(obrácené lomítko).
Rozšířené regulární výrazy #
Chcete-li vzor interpretovat jako rozšířený regulární výraz, použijte -E
(nebo --extended-regexp
) možnost. Rozšířené regulární výrazy zahrnují všechny základní metaznaky spolu s dalšími metaznaky pro vytvoření složitějších a výkonnějších vzorců vyhledávání. Níže je několik příkladů:
-
Porovnejte a extrahujte všechny e-mailové adresy z daného souboru:
grep -E -o "\b[A-Za-z0-9._%+-]+@[A-Za-z0-9.-]+\.[A-Za-z]{2,6}\b" file.txt
-
Porovnejte a extrahujte všechny platné IP adresy z daného souboru:
grep -E -o '(25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)\.(25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)\.(25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)\.(25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)' file.txt
-o
volba se používá k tisku pouze shodného řetězce.
Vyhledat více řetězců (vzorů) #
Dva nebo více vyhledávacích vzorů lze spojit pomocí operátoru OR |
.
Ve výchozím nastavení grep
interpretuje vzor jako základní regulární výraz, kde jsou metaznaky jako |
ztrácejí svůj zvláštní význam a musí být použity jejich verze se zpětným lomítkem.
V níže uvedeném příkladu hledáme všechny výskyty slov fatal
, error
a critical
v souboru logerror Nginx:
grep 'fatal\|error\|critical' /var/log/nginx/error.log
Pokud použijete možnost rozšířeného regulárního výrazu -E
, pak operátor |
by nemělo být escapováno, jak je uvedeno níže:
grep -E 'fatal|error|critical' /var/log/nginx/error.log
Vytisknout řádky před zápasem #
Chcete-li vytisknout určitý počet řádků před odpovídajícími řádky, použijte -B
(nebo --before-context
).
Chcete-li například zobrazit pět řádků úvodního kontextu před odpovídajícími řádky, použijte následující příkaz:
grep -B 5 root /etc/passwd
Tisk řádků po zápase #
Chcete-li vytisknout určitý počet řádků po odpovídajících řádcích, použijte -A
(nebo --after-context
).
Chcete-li například zobrazit pět řádků koncového kontextu po odpovídajících řádcích, použijte následující příkaz:
grep -A 5 root /etc/passwd
Závěr č.
grep
umožňuje vyhledávat vzor uvnitř souborů. Pokud je nalezena shoda, grep vytiskne řádky obsahující zadaný vzor.
Na stránce Uživatelské příručky Grep se můžete o Grepu dozvědět mnohem více.
Pokud máte nějaké dotazy nebo zpětnou vazbu, neváhejte zanechat komentář.