Muszę znaleźć (lub dokładniej policzyć) wszystkie pliki, które pasują do tego wzorca.Rekursywnie znaleźć wszystkie pliki, które pasują do określonego wzorca
*/foo/* doc
Jeżeli pierwsza wieloznaczny gwiazdka obejmuje zmienną liczbę podkatalogów.
Muszę znaleźć (lub dokładniej policzyć) wszystkie pliki, które pasują do tego wzorca.Rekursywnie znaleźć wszystkie pliki, które pasują do określonego wzorca
*/foo/* doc
Jeżeli pierwsza wieloznaczny gwiazdka obejmuje zmienną liczbę podkatalogów.
GNU znaleźć można użyć wyrażenia regularnego, które (w przeciwieństwie -name
) pasujące całą ścieżkę:
find . -regex '.*/foo/[^/]*.doc'
po prostu policzyć liczbę plików:
find . -regex '.*/foo/[^/]*.doc' -printf '%i\n' | wc -l
(Przyczyny kod formatu %i
find
, aby wydrukować numer i-węzła zamiast nazwy pliku, w przeciwieństwie do nazwy pliku, numer i-węzła gwarantuje, że nie będzie miał znaków takich jak znak nowej linii, więc liczenie jest bardziej wiarygodne. Dzięki @tripleee za sugestię.)
Nie wiem, czy to zadziała na OSX.
Dołącz "| wc -l" na koniec tego i jest idealny. – pw222
jak about:
find BASE_OF_SEARCH/*/foo -name \*.doc -type f | wc -l
Co to robi:
Zaletą tej metody:
AKTUALIZACJA: potrzebujesz zmiennej głębokości? ok:
find BASE_OF_SEARCH -name \*.doc -type f | grep foo | wc -l
Opcjonalnie można odfiltrować wyniki, które mają "foo" w pliku imię i nazwisko, ponieważ pokaże to również.
Działa to z wyjątkiem faktu, że nie działa z głębokością podkatalogu zmiennej pomiędzy BASE_OF_SEARCH a foo. Być może nie byłem wystarczająco jasny z tą specyfikacją. Jest na tyle blisko, że mogłem wykonać zadanie, które zamierzałem wykonać, a więc przegłosować i podziękować. – pw222
Należy podkreślić, że nie jest rekurencyjny. Jednak często nie jest to konieczne. To jest proste i sympatyczne rozwiązanie. Choć może to mieć problemy z wydajnością - nie wiem. – robsch
Dodałem funkcję dla Twoich żądań – MonkeyWidget
Nietestowane, ale spróbuj:
find . -type d -name foo -print | while read d; do echo "$d/*.doc" ; done | wc -l
znaleźć wszystkie „foo” katalogów (na różnych głębokościach) (ta ignoruje dowiązania, jeśli jest to część problemu można dodać je); użyj globowania powłoki, aby znaleźć wszystkie pliki ".doc", a następnie policz je.
Pętla 'while' jest w pełni redundantna i nieco podatna na błędy. Ponadto symbol wieloznaczny nie zostanie rozwinięty, ponieważ jest cytowany. Po prostu wpisz 'find -print' na' wc -l'. Będzie to jednak powodować niepoprawną liczbę, jeśli nazwa pliku zawiera znak nowej linii. – tripleee
Czy to musi być bash? zsh może to zrobić, używając składni 'ls **/foo/* .doc'. – Alastair
Alastair, dzięki za sugestię. Nie wiedziałem o zsh i jego podwójnej składni. Co ciekawe, wynikowa rozszerzona lista argumentów jest zbyt długa dla ls (około 6000 nazw plików) i daje błąd. – pw222
Bash v4 obsługuje także rekurencyjny glob "**". – tripleee