Como mover os primeiros x arquivos

21

Eu tenho essa pasta enorme com milhares de arquivos não ordenados. É possível mover os primeiros 5000s para uma subpasta através do mvcomando? Por enquanto, movo arquivos com

 mv *some_pattern* ./subfolder1/

Por enquanto, movo imagens aleatoriamente, não é realmente importante se não houver exatamente 5000 arquivos em cada subpasta. Tem algum jeito melhor de fazer isso?

Fabinout
fonte

Respostas:

23
mv `ls | head -500` ./subfolder1/
Schaiba
fonte
12
(assumindo que nenhum dos nomes de arquivos contêm espaço, tabulação, nova linha, estrela, colchete aberto, caracteres ponto de interrogação ou começar com -ou .e assumindo subfolder1em si não aparecer nessa lista.)
Stéphane Chazelas
@ StéphaneChazelas se o arquivo contiver esses arquivos, como podemos modificar o comando?
Peiti Li 10/11
$ sudo mv `ls | head -50000` 01/ sudo: unable to execute /bin/mv: Argument list too long
Brian Thomas
15

Com zsh:

mv -- *(D.oN[1,5000]) ./subfolder1

Para mover até 5000 arquivos regulares na ordem em que estão no diretório

Para os primeiros 5000 na lista classificada lexicograficamente:

mv -- *(D.[1,5000]) ./subfolder1

Se você receber um erro sobre a lista arg por muito tempo . Você pode usar zsho mvcomando buitin emitindo:

zmodload zsh/files

primeiro.

POSIXly:

set --
for f in .* *; do
  [ "$#" -lt 5000 ] || break
  [ -f "$f" ] || continue
  [ -L "$f" ] && continue
  set -- "$@" "$f"
done
mv -- "$@" subfolder1/
Stéphane Chazelas
fonte
2
O snippet POSIX é uma jóia
iruvar
e se eu receber o erro usando o bash?
Brian Thomas
8

Uma versão que é simples e suporta caracteres especiais, espaços etc.

ls -Q dir1 | head -1000 | xargs -i mv dir1/{} dir2/

Para que isso funcione como está, dir2deve existir e você deve executá-lo a partir do diretório pai de dir1e dir2.

Isso moverá 1000 arquivos de dir1 para dir2.

Luis Antolín Cano
fonte
Agradável! ls -Q -S dir1 | head -1000 | xargs -i mv dir1/{} dir2/ para mover 1000 maiores arquivos em dir1 (-S arquivo de listas por tamanho)
oneklc
1
Observe que ls -Qnão produz uma saída compatível com xargso formato de entrada esperado. Ajuda para nomes de arquivos que contêm caracteres de espaço, mas não para aspas duplas ou barras invertidas e prejudica nomes de arquivos que contêm caracteres de controle, incluindo TAB.
Stéphane Chazelas
3

Pode ser necessário fazer algo assim:

x=1
for file in *
do
    if [ "X$x" = "X#####" ]; then
        break
    fi
    mv $file <destination>
    x=`expr $x + 1`
done

Esse script funciona em bash, ksh, sh e em várias variantes do UNIX.

Karlson
fonte
1
(desde que nenhum dos nomes de arquivos contenha espaço, tab, nova linha, estrela, colchete aberto, caracteres de ponto de interrogação ou comece com - ou. e destinationse ele não aparecer nessa lista.)
Stéphane Chazelas
@StephaneChazelas True. Esta não é uma solução completa, apenas um método de lidar com o problema.
11133 Karlson
3
  1. Vá para o diretório do qual você deseja mover os arquivos
  2. comando abaixo

    find . -name 'Hello*.gz' | head -n 5000 | xargs -I {} mv {} /data01/path/ 

No findcomando, .(ponto) indica o diretório atual

localiza arquivos que começam com Hello e terminam com gz, os primeiros 5000 arquivos serão movidos para o caminho /data01/path/

Pratik Hiremath
fonte
1

Consegui fazer um movimento de 50.000 com sucesso sem o erro mv bash como este

 ls | head -50000 | xargs -I{} sudo mv {} 01/

O engraçado é que isso foi em um compartilhamento de samba; portanto, o limite de 50k é porque a GUI do Windows Explorer não gosta de mais de 60k arquivos em um diretório em geral.

Brian Thomas
fonte