Нахождение редких файлов?

Как отмечено жильем ed не может сделать этого. Большинство операций редактирования требует, чтобы файл был переписан, только замены могут быть сделаны оперативные, в этом случае Вы могли использовать hexedit(1).

Наименьшее количество памяти голодный путь состоит в том, чтобы использовать sed операции, например, заменять август июнем на первой строке:

sed '1s/August/June/' FILE > NEWFILE
19
12.08.2013, 22:13
4 ответа

В системах (и файловые системы) поддержка SEEK_HOLE lseek флаг (как Ваша Ubuntu 12.04 на ext4 был бы), и принятие значения для SEEK_HOLE 4, как это находится на Linux:

if perl -le 'seek STDIN,0,4;$p=tell STDIN;
   seek STDIN,0,2; exit 1 if $p == tell STDIN'< the-file; then
  echo the-file is sparse
else
  echo the-file is not sparse
fi

Тем синтаксисом оболочки является POSIX. Непортативный материал в нем perl и это SEEK_HOLE.

lseek(SEEK_HOLE) ищет на запуск первой дыры в файле или конец файла, если никакая дыра не найдена. Выше мы знаем, что файл не редок когда lseek(SEEK_HOLE) берет нас в конец файла (к тому же месту как lseek(SEEK_END)).

Если Вы хотите перечислить редкие файлы:

find . -type f ! -size 0 -exec perl -le 'for(@ARGV){open(A,"<",$_)or
  next;seek A,0,4;$p=tell A;seek A,0,2;print if$p!=tell A;close A}' {} +

GNU find (начиная с версии 4.3.3), имеет -printf %S сообщить о разреженности файла. Это проявляет тот же подход как frostschutz' ответ, в котором это берет отношение использования диска по сравнению с размером файла, так, как гарантируют, не сообщит обо всех редких файлах (как то, когда существует сжатие на уровне файловой системы или где свободное место, оставленное дырами, не компенсирует инфраструктуру файловой системы служебные или большие расширенные атрибуты), но работал бы над системами, которые не имеют SEEK_HOLE или файловые системы, где SEEK_HOLE не реализован. Здесь с инструментами GNU:

find . -type f ! -size 0 -printf '%S:%p\0' |
  awk -v RS='\0' -F : '$1 < 1 {sub(/^[^:]*:/, ""); print}'

(обратите внимание, что более ранняя версия этого ответа не работала правильно когда find выраженный разреженность что касается экземпляра 3.2e-05. Благодаря ответу @flashydave для того, чтобы обратить мое внимание на него)

11
27.01.2020, 19:45
  • 1
    Тот же комментарий как выше; я ищу способ найти все редкие файлы, не проверяют конкретный файл. –  Andrew Ferrier 12.08.2013, 22:12
  • 2
    Возможно, find должен также исключить 0 файлов байта напрямую? –  frostschutz 12.08.2013, 22:56
  • 3
    @frostschutz, положительная сторона, ответ обновляется. –  Stéphane Chazelas 12.08.2013, 23:04
  • 4
    Хорошая находка с find -printf '%S'! :-) –  frostschutz 14.08.2013, 13:29
  • 5
    @Brian, замените tr команда с xargs -r0 rm -f –  Stéphane Chazelas 30.01.2017, 09:29

Вы можете найти разреженные файлы формата %Sвfind:

# find / -type f -printf "%S\t%p\n" | gawk '$1 < 1.0 {print}'
0.0139994       /var/log/lastlog
0.959592        /usr/lib/locale/locale-archive
...

Нашел в этой статье :https://www.thegeekdiary.com/how-to-find-all-the-sparse-file-in-linux/

4
17.03.2020, 16:50

Файл обычно редок, когда количество выделенных блоков меньше, чем размер файла (здесь использующий GNU stat как найдено на Ubuntu, но остерегаются, другие системы могут иметь несовместимые реализации stat).

if [ "$((`stat -c '%b*%B-%s' -- "$file"`))" -lt 0 ]
then
    echo "$file" is sparse
else
    echo "$file" is not sparse
fi

Вариант с find: (украденный от Stephane)

find . -type f ! -size 0 -exec bash -c '
    for f do
        [ "$((`stat -c "%b*%B-%s" -- "$f"`))" -lt 0 ] && printf "%s\n" "$f";
    done' {} +

Вы обычно помещали это в сценарий оболочки вместо этого, затем должностное лицо сценарий оболочки.

find . -type f ! -size 0 -exec ./sparsetest.sh {} +
8
27.01.2020, 19:45
  • 1
    Это не может работать, если редких блоков недостаточно для покрытия для издержек косвенных блоков в традиционных файловых системах, например, того, если сжатие вместо разреженности уменьшает сумму выделенного места. –  Stéphane Chazelas 12.08.2013, 20:28
  • 2
    Уверенный; SEEK_HOLE так же проблематично, хотя, как это не поддерживается многими платформами/файловыми системами. В Linux Вы могли также использовать FIEMAP/FIBMAP, но FIBMAP в особенности является ужасно медленным... там, просто, кажется, не хороший путь. –  frostschutz 12.08.2013, 20:51
  • 3
    Также много этих методов требует, чтобы файл синхронизировался сначала. –  frostschutz 12.08.2013, 20:57
  • 4
    Спасибо. Это действительно не отвечает на вопрос, все же. Я не надеюсь проверять, редок ли конкретный файл, но найти все редкие файлы в системе. –  Andrew Ferrier 12.08.2013, 22:11
  • 5
    @AndrewFerrier извините, я предполагаю, что думал, что это было достаточно тривиально для обертывания этого в a for file in * или find. Если можно протестировать единственный файл, можно протестировать все файлы..., хотя действительно необходимо исключить каталоги с этим методом. –  frostschutz 12.08.2013, 22:57

Ответ Stephane Chazelas выше не учитывает тот факт, что некоторые разреженные файлы с параметром find %S сообщают отношение как числа с плавающей точкой, например

9.31323e-09:./somedir/sparsefile.bin

Их можно найти дополнительно с помощью

find . -type f ! -size 0 -printf '%S:%p\0' |
   sed -zn '/^\(0[^:]*:\)\|\([0-9.]\+e-.*:\)/p' |
   tr '\0' '\n'
3
27.01.2020, 19:45

Теги

Похожие вопросы