Самый быстрый способ получить каталог Размер и Размер на диске - PullRequest
2 голосов
/ 23 сентября 2011

Я недавно ответил на аналогичный вопрос, но сейчас я хотел бы эмулировать с помощью bash функцию «Каталог -> Правый клик -> Свойства» Windows (см. Рис.).

enter image description here

Я смог воспроизвести что-то вроде Размер: в байтах, используя эту команду:

echo $(find . -type f -printf "%s+") | sed 's/+$//g' | bc

, что вполнебыстро, но возможно ли получить информацию быстрее (чем найти) или сделать математику быстрее (чем bc)?Кроме того, я бы использовал команду du -sb для эмуляции размера на диске: и, возможно, еще пару find для подсчета файлов и каталогов и эмуляции строки Contains: .

Есть ли лучшие способы подражать таким результатам?

Ответы [ 2 ]

2 голосов
/ 24 сентября 2011

Предполагается, Cygwin:

cd /cygdrive/c

printf "Size: %s", $( du --apparent-size -sh )
printf "Size on disk: %s", $( du  -sh )
find . -printf "%y\n" | awk '
  $1 == "d" {dirs++} 
  END {printf("Contains: %d files, %d folders\n", NR-dirs, dirs)}
'
1 голос
/ 24 сентября 2011

Я только что написал быструю и грязную утилиту, основанную на nftw (1) .

Утилита в основном представляет собой пример справочной страницы с добавленной статистикой.

Функциональный

Я выбрал

  • оставаться в пределах одной точки монтирования
  • не следовать символическим ссылкам (для простоты и , потому что обычно это то, что вы хотите)
  • обратите внимание, что он все равно будет подсчитывать размер символических ссылок : :)
  • он показывает видимый размер (длину файла) , а также размер на диске (выделенные блоки).

Тесты, скорость

Я тестировал бинарный файл (/ tmp / test) на своей коробке:

# clear page, dentry and attribute caches
echo 3> /proc/sys/vm/drop_caches 
time /tmp/test /

output

Total size: 28433001733
In 878794 files and 87047 directories (73318 symlinks and 0 inaccessible directories)
Size on disk 59942192 * 512b = 30690402304

real    0m2.066s
user    0m0.140s
sys 0m1.910s

Я не сравнивал ваш инструмент, но он кажется довольно быстрым.Возможно, вы можете взять исходный код и создать собственную версию для максимальной скорости?

Чтобы проверить, действительно ли редкие файлы действительно были правильно сообщены:

mkdir sparse
dd bs=1M seek=1024 count=0 of=sparse/file.raw
ls -l sparse/
./test sparse/

Вывод:

total 0
-rw-r--r-- 1 sehe sehe 1073741824 2011-09-23 22:59 file.raw

Total size: 1073741884
In 1 files and 1 directories (0 symlinks and 0 inaccessible directories)
Size on disk 0 * 512b = 0

Код

#define _XOPEN_SOURCE 500
#include <ftw.h>
#include <stdio.h>
#include <stdlib.h>
#include <stdint.h>

static uintmax_t total        = 0ul;
static uintmax_t files        = 0ul;
static uintmax_t directories  = 0ul;
static uintmax_t symlinks     = 0ul;
static uintmax_t inaccessible = 0ul;
static uintmax_t blocks512    = 0ul;

static int
display_info(const char *fpath, const struct stat *sb,
             int tflag, struct FTW *ftwbuf)
{
    switch(tflag)
    {
        case FTW_D:
        case FTW_DP:  directories++;  break;
        case FTW_NS:
        case FTW_SL:
        case FTW_SLN: symlinks++;     break;
        case FTW_DNR: inaccessible++; break;
        case FTW_F:   files++;        break;
    }
    total += sb->st_size;
    blocks512 += sb->st_blocks;
    return 0; /* To tell nftw() to continue */
}

int
main(int argc, char *argv[])
{
    int flags = FTW_DEPTH | FTW_MOUNT | FTW_PHYS;

    if (nftw((argc < 2) ? "." : argv[1], display_info, 20, flags) == -1)
    {
        perror("nftw");
        exit(EXIT_FAILURE);
    }

    printf("Total size: %7jd\n", total);
    printf("In %jd files and %jd directories (%jd symlinks and %jd inaccessible directories)\n", files, directories, symlinks, inaccessible);
    printf("Size on disk %jd * 512b = %jd\n", blocks512, blocks512<<9);

    exit(EXIT_SUCCESS);
}

Скомпилировать с ...

gcc test.c -o test
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...