Bash renomeia 360 000 arquivos usando find -exec

2

Eu tenho cerca de 360 000 arquivos como:

./001/1/1.jpg
./001/1/2.jpg
./001/2/1.jpg
./002/1/1.jpg
./003/1/1.jpg
...
pattern: [60 dirs]/[1000 subdirs]/[4-10 files].jpg

Eu quero renomear arquivos usando rename , por exemplo, de * .jpg para * .jpeg. Eu não posso fazer isso com único rename , porque eu recebo a lista de argumentos de erro é muito longo.

Procurando por solução, eu descobri isso, mas não renomeia nada:

find -maxdepth 2 -mindepth 2 -type d -exec rename -n 's/jpg/jpeg/' {}/* \;

Quando eu verifico se o {} está expandido substituindo renomear por echo:

find -maxdepth 2 -mindepth 2 -type d -exec echo "rename -n 's/jpg/jpeg/' {}/*" \;

Eu recebo o resultado esperado:

rename -n 's/jpg/jpeg/' ./061/61430/*
rename -n 's/jpg/jpeg/' ./061/61431/*
...

Se eu executar qualquer um desses comandos de renomeação, eu renomeio os trabalhos. Então, o problema deve ser com o {} .

Obrigado pela ajuda!

    
por koubic 06.01.2015 / 12:21

5 respostas

3
find  | prename 's/\.jpg$/.jpeg/'

ou se você tiver arquivos oder no diretório atual

find 0[0-9][0-9] | prename 's/\.jpg$/.jpeg/'
    
por 06.01.2015 / 12:41
4

Na primeira instância, * é expandido pelo shell antes de chegar a rename (se for expandido - duvido que qualquer coisa corresponda a {}/* ) e, se não for expandido, o comando que é executado é rename com os três argumentos -n , s/jpg/jpeg/ e some/path/* . Esse último argumento não é o nome de um arquivo existente, então rename não faz nada.

Sem shell globbing, o caminho é inútil para rename .

Então, em vez disso, faça:

find -maxdepth 3 -mindepth 3 -type f -iname '*.jpg' -exec rename -n 's/jpg$/jpeg/i' {} +

Use a capacidade de find de criar linhas de comando o maior tempo possível com + em vez de ; .

    
por 06.01.2015 / 13:09
1

Aqui está uma maneira alternativa de rename estar ausente:

find 0[0-6][0-9] -name "*.jpg" -exec sh -c 'for i do echo mv "$i" "${i%g}eg"; done' sh {} + 
    
por 06.01.2015 / 14:38
0

Você não deve especificar type d , a menos que queira renomear apenas diretórios. Para alterar as extensões .jpg para .jpeg try

find . -maxdepth 2 -mindepth 2 -name '*.jpg' -exec sh -c 'echo mv -- "$0" "${0%%.jpg}.jpeg"' {} \;

Remova echo se você gostar do que vê na tela.

    
por 06.01.2015 / 13:03
0

Usando o cygwin, minha versão de renomeação não tem a substituição de regex, nem sua sintaxe rename [options] expression replacement file... parece funcionar. Além disso, as sugestões do bash falham com

... -c: line 0: unexpected EOF while looking for matching '"'
... -c: line 1: syntax error: unexpected end of file

Ai ... sempre há perl:

perl -MFile::Find -e 'find(sub{return unless /^(.*)\.jpg$/;'mv $_ $1.jpeg'}, ".")'
    
por 01.07.2016 / 22:38