Classificação de arquivos de acordo com o tamanho recursivamente

78

Preciso encontrar os maiores arquivos em uma pasta.
Como digitalizo uma pasta recursivamente e classifico o conteúdo por tamanho?

Eu tentei usar ls -R -S, mas isso lista os diretórios também.
Eu também tentei usar find.

user2179293
fonte
1
Deseja listar os arquivos em cada subdiretório separadamente ou deseja localizar todos os arquivos em todos os subdiretórios e listá-los por tamanho, independentemente de qual subdiretório eles estejam? Além disso, o que você quer dizer com "diretório" e "pasta"? Você parece usá-los para descrever coisas diferentes.
terdon
Você está dizendo que deseja apenas listar os arquivos em um determinado diretório, bem como os arquivos em seus subdiretórios, sem mostrar apenas os subdiretórios? Por favor, tente limpar sua pergunta, não está muito claro.
slm

Respostas:

92

Você também pode fazer isso com apenas du. Só por segurança, estou usando esta versão do du:

$ du --version
du (GNU coreutils) 8.5

A abordagem:

$ du -ah ..DIR.. | grep -v "/$" | sort -rh

Repartição da abordagem

O comando du -ah DIRproduzirá uma lista de todos os arquivos e diretórios em um determinado diretório DIR. O -hproduzirá tamanhos legíveis por humanos que eu prefiro. Se você não os quiser, abandone esse interruptor. Estou usando o head -6just para limitar a quantidade de saída!

$ du -ah ~/Downloads/ | head -6
4.4M    /home/saml/Downloads/kodak_W820_wireless_frame/W820_W1020_WirelessFrames_exUG_GLB_en.pdf
624K    /home/saml/Downloads/kodak_W820_wireless_frame/easyshare_w820.pdf
4.9M    /home/saml/Downloads/kodak_W820_wireless_frame/W820_W1020WirelessFrameExUG_GLB_en.pdf
9.8M    /home/saml/Downloads/kodak_W820_wireless_frame
8.0K    /home/saml/Downloads/bugs.xls
604K    /home/saml/Downloads/netgear_gs724t/GS7xxT_HIG_5Jan10.pdf

Fácil o suficiente para classificá-lo do menor para o maior:

$ du -ah ~/Downloads/ | sort -h | head -6
0   /home/saml/Downloads/apps_archive/monitoring/nagios/nagios-check_sip-1.3/usr/lib64/nagios/plugins/check_ldaps
0   /home/saml/Downloads/data/elasticsearch/nodes/0/indices/logstash-2013.04.06/0/index/write.lock
0   /home/saml/Downloads/data/elasticsearch/nodes/0/indices/logstash-2013.04.06/0/translog/translog-1365292480753
0   /home/saml/Downloads/data/elasticsearch/nodes/0/indices/logstash-2013.04.06/1/index/write.lock
0   /home/saml/Downloads/data/elasticsearch/nodes/0/indices/logstash-2013.04.06/1/translog/translog-1365292480946
0   /home/saml/Downloads/data/elasticsearch/nodes/0/indices/logstash-2013.04.06/2/index/write.lock

Inverta, do maior para o menor:

$ du -ah ~/Downloads/ | sort -rh | head -6
10G /home/saml/Downloads/
3.8G    /home/saml/Downloads/audible/audio_books
3.8G    /home/saml/Downloads/audible
2.3G    /home/saml/Downloads/apps_archive
1.5G    /home/saml/Downloads/digital_blasphemy/db1440ppng.zip
1.5G    /home/saml/Downloads/digital_blasphemy

Não me mostre o diretório, apenas os arquivos:

$ du -ah ~/Downloads/ | grep -v "/$" | sort -rh | head -6 
3.8G    /home/saml/Downloads/audible/audio_books
3.8G    /home/saml/Downloads/audible
2.3G    /home/saml/Downloads/apps_archive
1.5G    /home/saml/Downloads/digital_blasphemy/db1440ppng.zip
1.5G    /home/saml/Downloads/digital_blasphemy
835M    /home/saml/Downloads/apps_archive/cad_cam_cae/salome/Salome-V6_5_0-LGPL-x86_64.run

Se você deseja apenas a lista dos menores para os maiores, mas os 6 principais arquivos incorretos, você pode reverter a opção de classificação, soltar ( -r) e usar em tail -6vez do head -6.

$ du -ah ~/Downloads/ | grep -v "/$" | sort -h | tail -6
835M    /home/saml/Downloads/apps_archive/cad_cam_cae/salome/Salome-V6_5_0-LGPL-x86_64.run
1.5G    /home/saml/Downloads/digital_blasphemy
1.5G    /home/saml/Downloads/digital_blasphemy/db1440ppng.zip
2.3G    /home/saml/Downloads/apps_archive
3.8G    /home/saml/Downloads/audible
3.8G    /home/saml/Downloads/audible/audio_books
slm
fonte
14
A grep -v "/$"parte não parece estar fazendo o que você esperava, pois os diretórios não têm uma barra anexada. Alguém sabe como excluir diretórios dos resultados?
Jan Warchoł 16/02
@JanekWarchol - qual versão do coreutils você está usando?
Slm
Estou no 8.13. De qualquer forma, a saída da sua resposta também não tem /s à direita - por exemplo, /home/saml/Downloads/audibleparece ser um diretório, mas não possui uma barra. Só /home/saml/Downloads/tem uma barra, mas é provavelmente porque você a escreveu com uma barra ao especificar o argumento para inicial du.
Jan Warchoł
1
Isso encontra dirs também
ekerner 17/08/19
1
Isso não lista apenas os arquivos, mas também os diretórios :(
Roman Gaufman
20

Se você deseja encontrar todos os arquivos no diretório atual e seus subdiretórios e listá-los de acordo com seu tamanho (sem considerar o caminho) e assumindo que nenhum dos nomes de arquivo contenha caracteres de nova linha, com o GNU find, você pode fazer o seguinte:

find . -type f -printf "%s\t%p\n" | sort -n

A partir man findde um sistema GNU:

   -printf format
          True; print format  on  the  standard  output,
          interpreting  `\'  escapes and `%' directives.
          Field widths and precisions can  be  specified
          as  with the `printf' C function.  Please note
          that many of the  fields  are  printed  as  %s
          rather  than  %d, and this may mean that flags
          don't work as you  might  expect.   This  also
          means  that  the `-' flag does work (it forces
          fields to be  left-aligned).   Unlike  -print,
          -printf  does  not add a newline at the end of
          the string.  The escapes and directives are:

          %p     File's name.
          %s     File's size in bytes.

De man sort:

   -n, --numeric-sort
          compare according to string numerical value
terdon
fonte
Infelizmente, não funciona no Mac, mostra: find: -printf: primário ou operador desconhecido
Roman Gaufman
@RomanGaufman sim, é por isso que a resposta especifica a localização do GNU . Se você instalar as ferramentas GNU no seu Mac, elas também funcionarão lá.
terdon
11

Tente o seguinte comando:

ls -1Rhs | sed -e "s/^ *//" | grep "^[0-9]" | sort -hr | head -n20

Ele listará os 20 maiores arquivos do diretório atual recursivamente.

Nota: A opção -hpara sortnão está disponível no OSX / BSD, portanto você deve instalar a sortpartir de coreutils(por exemplo, via brew) e aplicar o caminho do compartimento local para PATH, por exemplo

export PATH="/usr/local/opt/coreutils/libexec/gnubin:$PATH" # Add a "gnubin" for coreutils.

Como alternativa, use:

ls -1Rs | sed -e "s/^ *//" | grep "^[0-9]" | sort -nr | head -n20

Para os maiores diretórios du, use , por exemplo:

du -ah . | sort -rh | head -20

ou:

du -a . | sort -rn | head -20
kenorb
fonte
3
Perfeito, esta é a primeira solução que funciona no Mac e não mostra diretórios :) - obrigado!
Roman Gaufman
como filtrar para mostrar apenas arquivo com número de linhas> = X? (X = 0 para exemplo)
Matrix
7

Isso localizará todos os arquivos recursivamente e os classificará por tamanho. Ele imprime todos os tamanhos de arquivo em kb e arredonda para baixo para que você possa ver arquivos de 0 KB, mas estava perto o suficiente para meus usos e funciona no OSX.

find . -type f -print0 | xargs -0 ls -la | awk '{print int($5/1000) " KB\t" $9}' | sort -n -r -k1

Brad Parks
fonte
também trabalhou no Ubuntu 14.04!
David Lam
Isso lista diretórios, não apenas arquivos :(
Roman Gaufman
@RomanGaufman - obrigado pelo feedback! dos meus testes, find . -type flocaliza arquivos ... funciona recursivamente, você está certo, mas lista todos os arquivos que encontra, não os diretórios em si #
Brad Parks
Xargs foi usado na década de 1980. É uma má idéia desde 1989, quando o execplus foi introduzido por David Korn.
schily
5

Com zsh, você encontrará o maior arquivo (em termos de tamanho aparente, como a coluna de tamanho na ls -lsaída, não o uso do disco) com:

ls -ld -- **/*(DOL[1])

Para os 6 maiores:

ls -ld -- **/*(DOL[1,6])

Para classificar esses por tamanho de arquivo, você pode usar lsa -Sopção 's . Algumas lsimplementações também têm uma -Uopção para lsnão classificar a lista (como ela já está classificada por tamanho zshaqui).

Stéphane Chazelas
fonte
3

Solução simples para Mac / Linux que ignora diretórios:

find . -type f -exec du -h {} \; | sort -h
mprcela
fonte
2

O equivalente em BSDou OSXé

$ du -ah simpl | sort -dr | head -6
hanxue
fonte
0

Essa é uma necessidade incrivelmente comum por vários motivos (eu gosto de encontrar o backup mais recente em um diretório) e é uma tarefa surpreendentemente simples.

Vou fornecer uma solução Linux que usa os utilitários find, xargs, stat, tail, awk e sort.

A maioria das pessoas forneceu respostas únicas, mas eu prefiro as minhas porque lida corretamente com nomes de arquivos e o caso de uso pode ser facilmente alterado (modificar estatísticas e argumentos de classificação)

Também fornecerei uma solução Python que deve permitir que você use essa funcionalidade, mesmo no Windows

Solução de linha de comando Linux

Retornar recursivamente a lista inteira de apenas arquivos de um diretório, classificados por tamanho de arquivo

find . -type f -print0 | xargs -0 -I{} stat -c '%s %n' {} | sort -n

O mesmo de antes, mas desta vez, retorne o maior arquivo.

# Each utility is split on a new line to help 
# visualize the concept of transforming our data in a stream
find . -type f -print0 | 
xargs -0 -I{} stat -c '%s %n' {} | 
sort -n | 
tail -n 1 |
awk '{print $2}'

Mesmo padrão exato, mas agora selecione o arquivo mais novo em vez do maior

# (Notice only the first argument of stat changed for new functionality!)
find . -type f -print0 | xargs -0 -I{} stat -c '%Y %n' {} | 
sort -n | tail -n 1 | awk '{print $2}'

Explicação:

  1. find: localiza recursivamente todos os arquivos do diretório atual e os imprime com um caractere nulo
  2. xargs: utilitário para executar comandos usando argumentos fornecidos a partir da entrada padrão. Para cada linha de saída, queremos executar o utilitário stat nesse arquivo
  3. stat: Stat é um comando impressionante que possui muitos casos de uso. Estou imprimindo duas colunas, a primeira coluna sendo o tamanho do bloco (% s) e a segunda coluna sendo o nome do arquivo (% n)
  4. classificar: classifique os resultados com a chave numérica. Como o primeiro argumento é um número inteiro, nossos resultados serão classificados corretamente
  5. cauda: selecione apenas a última linha de saída (como a lista está classificada, esse é o maior arquivo!)
  6. awk: selecione a segunda coluna, que contém o nome do arquivo, e é o maior arquivo em um diretório recursivo.

Solução Python

#!/usr/bin/env python
import os, sys
files = list()
for dirpath, dirname, filenames in os.walk(sys.argv[1]):
    for filename in filenames:
        realpath = os.path.join(dirpath, filename)
        files.append(realpath)
files_sorted_by_size = sorted(files, key = lambda x: os.stat(x).st_size)
largest_file = files_sorted_by_size[-1]
print(largest_file)

Esse script demora um pouco mais para ser explicado, mas essencialmente, se você o salvar como script, ele pesquisará o primeiro argumento fornecido na linha de comando e retornará o maior arquivo desse diretório. O script não verifica erros, mas deve fornecer uma idéia de como abordar isso no Python, o que oferece uma boa maneira independente da plataforma de resolver esse problema.

Luke Pafford
fonte
0

Variante desta resposta de uma pergunta semelhante

find . -type f -exec du -ah {} + | sort -rh | more
crizCraig
fonte
0

Experimente o comando abaixo com a opção de classificação para ter pastas com tamanho em ordem crescente

du -sh * | sort -sh

Dhaval H. Nena
fonte
-1

Algo que funciona em qualquer plataforma, exceto AIX e HP-UX, é:

find . -ls | sort +6 | tail
esperto
fonte