Poate suna ca și când aș pune același lucru ca această întrebare , dar Am cerințe diferite. Acesta este un exemplu al sistemului meu de fișiere:
- / code /
- internal /
- dev /
- main /
- public /
- dev /
- main /
- release /
- instrumente /
- internal /
/code/internal/dev/
, /code/public/dev/
și /code/tools/
conțin subdirectoare pentru mai multe proiecte. Lucrez aproape exclusiv în ramurile dev ale /code/internal/
și /code/public/
și de multe ori vreau să caut un șir de text în acele directoare împreună cu /code/tools/
(care nu are ramuri). În aceste cazuri trebuie să fac trei comenzi separate:
$ grep -r "some string" /code/internal/dev/ $ grep -r "some string" /code/public/dev/ $ grep -r "some string" /code/tools/
Aș dori să știu dacă există o singură comandă pentru a face acest lucru. În caz contrar, cel mai probabil aș fi nevoie să scriu un script bash simplu.
A nswer
Puteți concatena mai multe căi pe care grep să le caute:
grep -r "some string" /code/internal/dev/ /code/public/dev/ /code/tools/
Comentarii
Răspuns
Dacă doriți să utilizați la maxim caracterele wildcard (iar ierarhia pe care ați postat-o este completă), puteți face
grep -r "some string" /code/{*/dev,tools}/*.cs
Explicație:
Primul pas realizat este extinderea listei braced. foo{bar,baz}qux
se extinde la foobarqux foobazqux
. Adică, există „un cuvânt separat generat pentru fiecare element separat din virgulă din listă, cu prefixul și partea postfix atașate fiecăruia. Puteți vedea cum funcționează acest lucru făcând
echo A{1,2,3,4}B
care produce
A1B A2B A3B A4B
Rețineți că acest lucru funcționează și cu mai multe paranteze și, de asemenea, cu argumente goale; de exemplu
echo {,1,2}{0,1,2}:{2,3}
dă
0:2 0:3 1:2 1:3 2:2 2:3 10:2 10:3 11:2 11:3 12:2 12:3 20:2 20:3 21:2 21:3 22:2 22:3
Deci, după extinderea bretelei, comanda dvs. arată astfel:
grep -r "some string" /code/*/dev/*.cs /code/tools/*.cs
Următorul pas este extinderea cu comodini. Știți deja că pentru partea *.cs
, dar funcționează și pentru directoare intermediare; dacă urmează un /
, se potrivesc doar directoarele. Prin urmare, dat fiind ierarhia dvs. (și alcătuind numele fișierelor pentru fișierele .cs
), dvs. Voi primi comanda:
grep -r "some string" /code/internal/dev/file1.cs /code/internal/dev/file2.cs /code/public/dev/file3.cs /code/tools/file4.cs /code/tools/file5.cs
Numai după ce toate acestea s-au întâmplat, grep
este apelat cu această listă de arg comentarii (rețineți că același lucru se întâmplă cu comenzile dvs. originale; grep
nu ajunge niciodată să vadă *
; extinderea care se face complet de bash
înainte de a apela grep
).
grep: /code/internal/dev/*.cs: No such file or directory
dacă nu elimin*.cs
din comandă. Aceasta este vina mea, deoarece am pus inițial*.cs
în întrebarea mea.