Bez nutnosti instalace varianty grep pcregrep
, můžete provést víceřádkové vyhledávání pomocí grep.
$ grep -Pzo "(?s)^(\s*)\N*main.*?{.*?^\1}" *.c
Vysvětlení:
-P
aktivujte perl-regexp pro grep (výkonné rozšíření regulárních výrazů)
-z
Zacházejte se vstupem jako se sadou řádků, z nichž každý je ukončen nulovým byte (znak ASCII NUL) namísto nového řádku. To znamená, že grep ví, kde jsou konce řádků, ale vstup vidí jako jeden velký řádek. Pozor, toto také přidává koncový znak NUL, pokud je použit s -o
, viz komentáře.
-o
tisknout pouze odpovídající. Protože používáme -z
, celý soubor je jako jeden velký řádek, takže pokud existuje shoda, vytiskne se celý soubor; tímto způsobem to neudělá.
V regulárním výrazu:
(?s)
aktivujte PCRE_DOTALL
, což znamená, že .
najde jakýkoli znak nebo nový řádek
\N
najít cokoliv kromě nového řádku, dokonce i s PCRE_DOTALL
aktivován
.*?
najděte .
v non-chamtivém režimu, to znamená, že se zastaví co nejdříve.
^
najít začátek řádku
\1
zpětný odkaz na první skupinu (\s*
). Toto je pokus najít stejné odsazení metody.
Jak si dokážete představit, toto vyhledávání vypíše hlavní metodu v C (*.c
) zdrojový soubor.
Nejsem moc dobrý v grepu. Ale váš problém lze vyřešit pomocí příkazu AWK. Stačí se podívat na
awk '/select/,/from/' *.sql
Výše uvedený kód bude výsledkem prvního výskytu select
do první sekvence from
. Nyní musíte ověřit, zda vrácené příkazy mají customername
nebo ne. K tomu můžete výsledek zpracovat. A můžete znovu použít awk nebo grep.