Question

J'ai quelques fichiers sur plusieurs dossiers:

/home/d/folder1/a.txt
/home/d/folder1/b.txt
/home/d/folder1/c.mov
/home/d/folder2/a.txt
/home/d/folder2/d.mov
/home/d/folder2/folder3/f.txt

Comment puis-je mesurer la grande quantité totale d'espace disque occupé par tous les fichiers txt dans / home / d /?

Je sais que du me donner l'espace total d'un dossier donné et ls -l me donnera l'espace total de fichiers individuels , mais si je veux d'additionner tous les fichiers txt et il suffit de regarder à la espace occupé par tous les fichiers txt dans un total de géant pour tous txt dans / home / d / y compris les folder1 et dossier2 et leurs sous-dossiers comme folder3 ?

Était-ce utile?

La solution

fera:

total=0
for file in *.txt
do
    space=$(ls -l "$file" | awk '{print $5}')
    let total+=space
done
echo $total

Autres conseils

find folder1 folder2 -iname '*.txt' -print0 | du --files0-from - -c -s | tail -1

rapportera l'utilisation de l'espace disque en octets par extension:

find . -type f -printf "%f %s\n" |
  awk '{
      PARTSCOUNT=split( $1, FILEPARTS, "." );
      EXTENSION=PARTSCOUNT == 1 ? "NULL" : FILEPARTS[PARTSCOUNT];
      FILETYPE_MAP[EXTENSION]+=$2
    }
   END {
     for( FILETYPE in FILETYPE_MAP ) {
       print FILETYPE_MAP[FILETYPE], FILETYPE;
      }
   }' | sort -n

Sortie:

3250 png
30334451 mov
57725092729 m4a
69460813270 3gp
79456825676 mp3
131208301755 mp4

simple:

du -ch *.txt

Si vous voulez juste l'espace total prises pour se présenter, puis:

du -ch *.txt | tail -1

Voici une façon de le faire (sous Linux, en utilisant GNU coreutils du et la syntaxe Bash), évitant mauvaise pratique :

total=0
while read -r line
do
    size=($line)
    (( total+=size ))
done < <( find . -iname "*.txt" -exec du -b {} + )
echo "$total"

Si vous voulez exclure le répertoire courant, utilisez -mindepth 2 avec find.

Une autre version qui ne nécessite pas la syntaxe de Bash:

find . -iname "*.txt" -exec du -b {} + | awk '{total += $1} END {print total}'

Notez que ceux-ci ne fonctionnent pas correctement avec les noms de fichiers qui comprennent des sauts de ligne (mais ceux qui ont des espaces Travaillera).

macOS

  • utilisez l'outil du et le paramètre -I pour exclure tous les autres fichiers

Linux

-X, --exclude-from=FILE
              exclude files that match any pattern in FILE

--exclude=PATTERN
              exclude files that match PATTERN

trouver GNU,

find /home/d -type f -name "*.txt" -printf "%s\n" | awk '{s+=$0}END{print "total: "s" bytes"}'

Miser sur ce ennuikiller, cela gérer les espaces dans les noms. Je devais faire cela et un petit rapport:

trouver -type f -name "* .wav" | grep export | ./calc_space

#!/bin/bash
# calc_space
echo SPACE USED IN MEGABYTES
echo
total=0
while read FILE
do
    du -m "$FILE"
    space=$(du -m "$FILE"| awk '{print $1}')
    let total+=space
done
echo $total

A une doublure pour ceux avec des outils GNU sur bash:

for i in $(find . -type f | perl -ne 'print $1 if m/\.([^.\/]+)$/' | sort -u); do echo "$i"": ""$(du -hac **/*."$i" | tail -n1 | awk '{print $1;}')"; done | sort -h -k 2 -r

Vous devez avoir activé extglob:

shopt -s extglob

Si vous voulez que les fichiers point à travailler, vous devez exécuter

shopt -s dotglob

Exemple de sortie:

d: 3.0G
swp: 1.3G
mp4: 626M
txt: 263M
pdf: 238M
ogv: 115M
i: 76M
pkl: 65M
pptx: 56M
mat: 50M
png: 29M
eps: 25M

etc

J'aime utiliser trouver en combinaison avec xargs:

find . -name "*.txt" -print0 |xargs -0 du -ch

Ajoutez la queue si vous voulez voir le grand total

find . -name "*.txt" -print0 |xargs -0 du -ch | tail -n1

ma solution pour obtenir une taille totale de tous les fichiers texte dans un chemin donné et sous-répertoires (en Perl oneliner)

find /path -iname '*.txt' | perl -lane '$sum += -s $_; END {print $sum}'

Pour tous ceux qui veulent le faire avec macOS à la ligne de commande, vous avez besoin d'une variation en fonction de l'argument -print0 au lieu de printf. Certaines des réponses ci-dessus adresse qui mais cela faire globalement par extension:

    find . -type f -print0 | xargs -0 stat -f "%N %i" |
  awk '{
      PARTSCOUNT=split( $1, FILEPARTS, "." );
      EXTENSION=PARTSCOUNT == 1 ? "NULL" : FILEPARTS[PARTSCOUNT];
      FILETYPE_MAP[EXTENSION]+=$2
    }
   END {
     for( FILETYPE in FILETYPE_MAP ) {
       print FILETYPE_MAP[FILETYPE], FILETYPE;
      }
   }' | sort -n

Il y a plusieurs problèmes potentiels avec la réponse acceptée:

  1. il ne descend pas dans les sous-répertoires (sans compter sur les fonctions du shell non standard comme globstar )
  2. en général, comme l'a souligné Dennis Williamson ci-dessous, vous devriez éviter analysant la sortie de ls
    • à savoir si l'utilisateur ou le groupe (colonnes 3 et 4) ont des espaces en eux, la colonne 5 ne sera pas la taille du fichier
  3. si vous avez un million de ces fichiers, ce pondra deux millions de sous-couches, et ce sera sloooow

proposé par ghostdog74 , vous pouvez utiliser l'option -printf GNU spécifique à find pour parvenir à une solution plus robuste, en évitant tous les tuyaux excessifs, sous-couches, Perl et étranges options du:

# the '%s' format string means "the file's size"
find . -name "*.txt" -printf "%s\n" \
  | awk '{sum += $1} END{print sum " bytes"}'

Oui, oui, des solutions utilisant paste ou bc sont également possibles, mais pas plus simple.

Sur Mac OS, vous devez utiliser Homebrew ou MacPorts installer findutils et appeler gfind à la place. (I voir le tag "linux" sur cette question, mais il est aussi tagged "unix".)

Sans GNU find, vous pouvez toujours revenir à l'aide du:

find . -name "*.txt" -exec du -k + \
  | awk '{kbytes+=$1} END{print kbytes " Kbytes"}'

... mais vous devez être conscient du fait que la sortie par défaut de du est blocs de 512 octets pour des raisons historiques (voir la section « LOGIQUE » ) et certaines versions de du (notamment, macOS de) ne sera même pas Vous une option pour imprimer la taille en octets.

Beaucoup d'autres solutions bien ici (voir de href="https://stackoverflow.com/a/14771141/785213"> Grange en particulier), mais la plupart souffrent l'inconvénient d'être inutilement complexes ou en fonction trop sur GNU ne dispose et peut-être dans votre environnement, c'est OK!

scroll top