Comment trouver la taille totale des fichiers groupés par extension


12

Je travaille sur un cluster partagé avec d'autres collègues. Le disque dur est limité (et a été plein à certaines occasions), donc je nettoie ma partie de temps en temps. Je veux le faire rapidement, donc jusqu'à présent je fais cela en faisant une liste de fichiers de plus de 100 Mo de plus de 3 mois, et je vois si j'en ai toujours besoin.

Mais maintenant, je pense qu'il pourrait y avoir un dossier avec> 1000 fichiers plus petits qui me manquent, donc je veux avoir un moyen facile de voir si c'est le cas. De la façon dont je génère des données, il serait utile d'obtenir une liste de la taille totale par extension. Dans le contexte de cette question, «extension» comme tout ce qui se trouve derrière le dernier point du nom de fichier.

Supposons que j'ai plusieurs dossiers avec plusieurs fichiers:

folder1/file1.bmp   40 kiB
folder1/file2.jpg   20 kiB
folder2/file3.bmp   30 kiB
folder2/file4.jpg    8 kiB

Est-il possible de faire une liste de la taille totale des fichiers par extension de fichier, comme ceci:

bmp 70 kiB
jpg 28 kiB

Je ne me soucie pas des fichiers sans extension, ils peuvent donc être ignorés ou mis dans une catégorie.

J'ai déjà parcouru les pages de manuel de ls, duet find, mais je ne sais pas quel est le bon outil pour ce travail ...


Cette question ne serait pas fausse sur codegolf.stackexchange.com :)
Doug McLean

@DougMcLean: vous êtes invités à le poster là-bas. ;)

Réponses:


16

Sur un système GNU:

find . -name '?*.*' -type f -printf '%b.%f\0' |
  awk -F . -v RS='\0' '
    {s[$NF] += $1; n[$NF]++}
    END {for (e in s) printf "%15d %4d %s\n", s[e]*512, n[e], e}' |
  sort -n

Ou la même chose avec perl, en évitant l' -printfextension de GNU find(toujours en utilisant une extension GNU -print0, mais celle-ci est plus largement prise en charge de nos jours):

find . -name '?*.*' -type f -print0 |
  perl -0ne '
    if (@s = stat$_){
      ($ext = $_) =~ s/.*\.//s;
      $s{$ext} += $s[12];
      $n{$ext}++;
    }
    END {
      for (sort{$s{$a} <=> $s{$b}} keys %s) {
        printf "%15d %4d %s\n",  $s{$_}<<9, $n{$_}, $_;
      }
    }'

Il donne une sortie comme:

          12288    1 pnm
          16384    4 gif
         204800    2 ico
        1040384   17 jpg
        2752512   83 png

Si vous voulez KiB, MiB... suffixes, dirigez-vous vers numfmt --to=iec-i --suffix=B.

%b*512donne l'utilisation du disque, mais notez que si les fichiers sont liés plusieurs fois en dur, ils seront comptés plusieurs fois afin que vous puissiez voir une différence avec les durapports.


Échoue sur MacOS (trouver: -printf: principal ou opérateur inconnu)
MichaelCodes

1
@MichaelCodes, oui -printfest spécifique à GNU find, c'est pourquoi j'ai dit sur un système GNU .
Stéphane Chazelas

@MichaelCodes, voir modifier avec une perlalternative qui devrait fonctionner même sur macOS.
Stéphane Chazelas

Qu'est-ce que 1,4,2,17? Le nombre de fichiers pour chaque type?
Jorge Cornejo Bellido

3

Voici une autre solution:

find . -type f |  egrep -o "\.[a-zA-Z0-9]+$" | sort -u | xargs -I '%' find . -type f -name "*%" -exec du -ch {} + -exec echo % \; | egrep "^\.[a-zA-Z0-9]+$|total$" | uniq | paste - -

La partie qui obtient les extensions est:

find . -type f |  egrep -o "\.[a-zA-Z0-9]+$" | sort -u

Recherchez ensuite les fichiers avec une extension et imprimez-les également à l'écran:

xargs -I '%' find . -type f -name "*%" -exec du -ch {} + -exec echo % \;

Ensuite, nous voulons conserver l'extension et le total:

egrep "^\.[a-zA-Z0-9]+$|total$" | uniq

et gardez-le sur la même ligne:

paste - -

Fonctionne sur MacOS.
MichaelCodes

2

Pas aussi agréable que la solution de Stéphane, mais vous pouvez essayer

find . -type f -name "*.png" -print0 | xargs -0r du -ch | tail -n1

où vous devez l'exécuter pour chaque type de fichiers.


1
Cela suppose qu'il existe suffisamment de fichiers png pour qu'une seule duinvocation soit exécutée. Avec GNU xargs, vous voudriez ajouter l' -rindicateur afin que du ne soit pas exécuté quand il n'y a pas de fichier (sinon, vous vous retrouveriez avec l'utilisation du disque du répertoire actuel). Vous souhaiterez peut-être ajouter un -type fou ! type dpour éviter de compter les fichiers qui se trouvent dans des répertoires dont le nom se termine par .png.
Stéphane Chazelas

cela ne recherche qu'une seule extension spécifique.
Rahul

Voilà ce que j'ai écrit. Il fallait l'envelopper dans un script qui itère sur toutes les extensions applicables afin d'obtenir une solution "complète".
contre-mode
En utilisant notre site, vous reconnaissez avoir lu et compris notre politique liée aux cookies et notre politique de confidentialité.
Licensed under cc by-sa 3.0 with attribution required.