Byłem zdezorientowany, dlaczego findkomenda drukuje również przycięte katalogi , i kilka innych zawiłych szczegółów na temat tego, jak -prunedziałało, ale udało mi się to z kilku przykładów.
Aby uruchomić poniższe przykłady, utwórz następujące katalogi i pliki.
mkdir aa
mkdir bb
touch file1
touch aa/file1
touch bb/file3
Aby utworzyć tę strukturę:
$ tree
.
├── aa
│ └── file1
├── bb
│ └── file3
└── file1
Teraz użyj find, aby wyszukać katalogi o nazwie aa. Tutaj nie ma problemu.
$ find . -type d -name aa
./aa
Poszukaj wszystkich katalogów innych niż aa, a my otrzymamy bieżący katalog .i ./bb, co również ma sens.
$ find . -type d ! -name aa
.
./bb
Jak dotąd tak dobrze, ale kiedy korzystamy -prune, find zwraca katalog, który przycinamy, co początkowo mnie zdezorientowało, ponieważ spodziewałem się, że zwróci wszystkie inne katalogi, a nie ten, który jest przycinany.
$ find . -type d -name aa -prune
./aa
Powód, dla którego zwraca przycinany katalog, został wyjaśniony nie w -prunesekcji stron podręcznika, jak wskazano w odpowiedzi Timo , ale w EXPRESSIONSsekcji:
Jeśli wyrażenie nie zawiera żadnych działań innych niż -prune,
-printwykonywane jest na wszystkich plikach, dla których wyrażenie jest prawdziwe.
co oznacza, że ponieważ wyrażenie pasuje do aanazwy katalogu, to wyrażenie będzie miało wartość true i zostanie wydrukowane, ponieważ find niejawnie dodaje znak „ -printna końcu” całego polecenia. Nie doda to -printjednak, jeśli celowo dodasz akcję -o -printdo końca:
find . -type d -name aa -prune -o -print
.
./file1
./bb
./bb/file3
Tutaj polecenie find NIE dodaje -printjuż niejawnego , więc katalog, który przycinamy ( aa), nie zostanie wydrukowany.
Wreszcie, jeśli dodamy klauzulę, która wyszukuje pliki o wzorcu nazw plików następującym file*po -o, musisz umieścić -printna końcu drugiej klauzuli w następujący sposób:
find . \( -type d -name aa -prune \) -o \( -type f -name 'file*' -print \)
./file1
./bb/file3
Powód, dla którego to działa, jest taki sam: jeśli nie umieścisz -printw drugiej klauzuli, to ponieważ nie ma innej akcji niż -pruneakcja, find doda -printautomatycznie na KONIEC polecenia, powodując -prunewydrukowanie klauzuli przycięty katalog:
find . \( \( -type d -name aa -prune \) -o \( -type f -name 'file*' \) \) -print
./aa
./file1
./bb/file3
Ogólnie rzecz biorąc, musisz umieścić -printpolecenie w drugiej klauzuli. Jeśli umieścisz go na środku, tak jak oryginalny plakat, nie będzie działał poprawnie, ponieważ przycinane pliki zostaną wydrukowane natychmiast, a druga klauzula nie będzie miała szansy wybrać plików, które chce:
find . \( -type d -name aa -prune -o -print \) -o \( -type f -name 'file*' \)
.
./file1
./bb
./bb/file3
Niestety, oryginalny plakat źle podał powyższe polecenie, umieszczając go -printw niewłaściwym miejscu. Mogło to zadziałać w jego konkretnym przypadku, ale nie działa w przypadku ogólnym.
Istnieją tysiące ludzi, którzy mają trudności ze zrozumieniem, jak -prunedziała. findStrona człowiek powinien być aktualizowany w celu zapobieżenia Niekończąca światową zamieszanie o tym poleceniu.
-print, w przeciwnym razie domniemanie-printdotyczy całego warunku