Jak usunąć wiele plików ze wspólnym prefiksem i sufiksem?

21

Mam wiele nazwanych plików

sequence_1_0001.jpg  
sequence_1_0002.jpg  
sequence_1_0003.jpg  
...

i nazwane pliki

sequence_1_0001.hmf  
sequence_1_0002.hmf  
sequence_1_0003.hmf  
...

i nazwane pliki

sequence_2_0001.jpg  
sequence_2_0002.jpg  
sequence_2_0003.jpg  
...

i

sequence_2_0001.hmf  
sequence_2_0002.hmf  
sequence_2_0003.hmf  
...

Chcę tylko usunąć pliki, które zaczynają się od „sekwencji_1” i kończą na „.hmf”, ale nie chcę ich usuwać jeden po drugim, ponieważ są tysiące plików. Jak mogę określić w poleceniu rm, że chcę usunąć wszystko, które zaczynają się od prefiksu „sekwencja_1” i kończą się na „.hmf”?

Obecnie pracuję z systemem RedHat Linux, ale chciałbym wiedzieć, jak to zrobić w innych dystrybucjach.

Paweł
źródło

Odpowiedzi:

28
rm sequence_1*.hmf

usuwa pliki zaczynające się sequence_1i kończące się na .hmf.


Globbing to proces, w którym twoja powłoka pobiera wzorzec i rozwija go do listy nazw plików pasujących do tego wzorca. Nie należy mylić go z wyrażeniami regularnymi, które są inne. Jeśli spędzasz większość czasu bash, Wiki Wooledge ma dobrą stronę na globbing (rozwijanie nazw ścieżek) . Jeśli chcesz mieć maksymalną przenośność, powinieneś przeczytać specyfikację POSIX na temat dopasowania wzorca również / zamiast tego.


W mało prawdopodobnym przypadku wystąpienia błędu „Zbyt długa lista argumentów” możesz spojrzeć na BashFAQ 95 , który to rozwiązuje. Najprostszym obejściem jest rozbicie wzorca globu na wiele mniejszych porcji, dopóki błąd nie zniknie. W twoim przypadku prawdopodobnie możesz uciec od podzielenia dopasowania przez prefiksy od 0 do 9 w następujący sposób:

for c in {0..9}; do rm sequence_1_"$c"*.hmf; done
rm sequence_1*.hmf  # catch-all case
jw013
źródło
Jest to bardzo sprytne obejście błędu „zbyt długa lista argumentów”. W moim przypadku mam dwadzieścia tysięcy plików, więc myślę, że musiałbym użyć pętli for od 0, .., 20. Dobrze?
Paul
@Paul Racja, po prostu podziel listę na tyle części, ile potrzebujesz, chociaż w pewnym momencie findpodejście staje się łatwiejsze niż zgadywanie i sprawdzanie.
jw013
14

Chociaż odpowiedź jw013 jest poprawna dla globowania wrt, to polecenie może się nie powieść, jeśli masz tysiące dopasowań: rozwinięta linia poleceń rm sequence_1_0001.hmf sequence_1_0002.hmf ...wygenerowana przez powłokę może być po prostu zbyt duża.

Jak sugerował Dom, możesz również użyć -deleteopcji z find:

find . -maxdepth 1 -type f -name 'sequence_1*.hmf' -delete

Zarówno -maxdepthi -delete, choć nie w standardzie POSIX, są dość powszechne w findimplementacjach na wolności. Dystrybucje Linuksa zazwyczaj używają GNU find, który z pewnością obsługuje te opcje.

Bezużyteczny
źródło
2
Jeśli możesz, użyj opcji -delete do znalezienia, nie rozwidla się dla każdego pliku ...
Dom
Dodano, na zdrowie. Wygląda na to, że -deletepowinien być obsługiwany w najnowszych systemach GNU i BSD, podczas gdy -print0jest tylko GNU. Prawdopodobnie jest też bardziej przenośny (chociaż nie powinien mieć znaczenia dla OP).
Bezużyteczne
Znalezienie przynajmniej OS X ma -print0, ale nie jest zawarte w POSIX.
Lri
5
rm sequence_1_{0000..0999}.hmf
rm sequence_1_{1000..1999}.hmf
rm sequence_1_{2000..2999}.hmf
...

działałby również w Bash.

nieznany użytkownik
źródło
Rozszerzenie nawiasów klamrowych wymaga bash, a forma wypełniona zerami wymaga wersji 4, jak sądzę.
jw013