Pregunta

Tengo algunos archivos en varias carpetas:

/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

¿Cómo puedo medir la cantidad total de espacio en disco ocupado por todos los archivos .txt en /home/d/?

du me dará el espacio total de una carpeta determinada, y ls -l me dará el espacio total de archivos individuales, pero ¿qué pasa si quiero sumar todos los archivos de texto y simplemente mirar el espacio ocupado por todos los archivos .txt en un total gigante ¿para todos los .txt en /home/d/ incluidas la carpeta1 y la carpeta2 y sus subcarpetas como la carpeta3?

¿Fue útil?

Solución

Esto hará que:

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

Otros consejos

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

Esto reportar el uso de espacio en disco en bytes por extensión:

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

Salida:

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

simple:

du -ch *.txt

Si lo que desea es el espacio total necesario para aparecer, a continuación:

du -ch *.txt | tail -1

Aquí hay una manera de hacerlo (en Linux, usando GNU coreutils du y la sintaxis de Bash), evitando href="http://mywiki.wooledge.org/ParsingLs" mala práctica :

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

Si desea excluir el directorio actual, utilice -mindepth 2 con find.

Otra versión que no requiere la sintaxis de Bash:

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

Tenga en cuenta que éstos no funcionarán correctamente con los nombres de archivo que incluyen saltos de línea (pero los que tienen espacios funcionará).

macOS

  • utilizar la herramienta y la du -I parámetro para excluir todos los otros archivos

Linux

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

--exclude=PATTERN
              exclude files that match PATTERN

GNU encontrar,

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

Sobre la base de ennuikiller, este se encargará de espacios en los nombres. Que tenía que hacer esto y conseguir un poco de informe:

encontrar -type f -name "* .wav" | grep exportación | ./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 un trazador de líneas para aquellos con herramientas GNU en 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

Debe tener activado extglob:

shopt -s extglob

Si desea archivos punto a trabajar, debe ejecutar

shopt -s dotglob

Resultado de muestra:

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.

Me gusta usar encontrar en combinación con xargs:

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

Añadir la cola si sólo desea ver el total general

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

mi solución para obtener un tamaño total de todos los archivos de texto en un camino y subdirectorios dado (usando oneliner Perl)

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

Para cualquiera que desee hacer esto con MacOS en la línea de comandos, se necesita una variación basada en el argumento -print0 en lugar de printf. Algunas de las respuestas anteriores que abordan pero esto va a hacer de manera integral por extensión:

    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

Hay varios problemas potenciales con la respuesta aceptada:

  1. no desciende a subdirectorios (sin depender de funciones de shell no estándar como globstar)
  2. En general, como lo señala Dennis Williamson a continuación, debe evitar analizando la salida de ls
    • es decir, si el usuario o grupo (columnas 3 y 4) tienen espacios, la columna 5 no tendrá el tamaño del archivo
  3. si tienes un millón de archivos de este tipo, esto generará dos millones de subcapas, y será lento

Como propuesto por Ghostdog74, puedes usar el específico de GNU -printf opción de find para lograr una solución más robusta, evitando todas las tuberías excesivas, subcapas, Perl y cosas raras. du opciones:

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

Sí, sí, soluciones usando. paste o bc También son posibles, pero no más sencillos.

En macOS, necesitarás usar Homebrew o MacPorts para instalar findutils, y llama gfind en cambio.(I ver la etiqueta "linux" en esta pregunta, pero también está etiquetada como "unix").

Sin GNU find, aún puedes recurrir al uso du:

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

…pero hay que tener en cuenta el hecho de que duLa salida predeterminada está en bloques de 512 bytes por razones históricas (ver la sección "JUSTIFICACIÓN" aquí), y algunas versiones de du (en particular, macOS) ni siquiera tener una opción para imprimir tamaños en bytes.

Muchas otras buenas soluciones aquí (ver La respuesta del granero. en particular), pero la mayoría sufre el inconveniente de ser innecesariamente compleja o depender demasiado de características exclusivas de GNU... ¡y tal vez en su entorno, eso esté bien!

Licenciado bajo: CC-BY-SA con atribución
No afiliado a StackOverflow
scroll top