Intereting Posts
Как указать требование для минимальной версии openssl в файле спецификации RPM? Почему разделитель не работает для расширения массива? Ubuntu – Двойной экран невозможно при крахе единства Сильное время загрузки ядра Linux; как исследовать на нем? Есть ли инструмент, который может контролировать использование полосы пропускания для одного процесса? Каково значение одиночных и двойных кавычек в переменных среды? Чтение двоичного файла в виде массива байтов или 16 или 32 бит с использованием сценария оболочки Есть ли способ проверить, был ли .so скомпилирован флаг -Bsymbolic-functions? несколько имен для одного узла в ssh_config Поиск и удаление подпапок, содержащих только самые последние Cat и Less дают разные результаты База данных mysql недоступна Как изменить размер корневого раздела в Debian? Как irqbalance определяет, какой пакет использовать? Как заставить grep игнорировать строки без завершающего символа новой строки

Как начать обработку файла со смещением?

Случай использования: у вас есть лог-файл с несколькими ГБ на целую неделю, и вам нужно искать что-то, что произошло в субботу, используя, например, grep . Сделав обоснованное предположение, вы предполагаете, что начало поиска из середины файла будет более чем вдвое сократить время обработки (так как это определенно не придется обрабатывать всю оставшуюся часть файла), не пропуская никаких релевантных данных. Это возможно?

Предполагая, что ваши данные находятся в хронологическом порядке:

  1. Получите размер файла, ищите его до конца и ftell() ;
  2. Разделите этот результат на 2;
  3. Используйте fseek() для поиска в этом месте;
  4. Ищите начало следующей строки, вызвав getline() один раз;
  5. Используйте strptime() чтобы узнать, на какую дату вы сейчас находитесь;
  6. Сделайте двоичный поиск, повторяя шаги 4 и 5, пока не найдете нужную строку.

Вы можете использовать dd по строкам:

 dd if=log skip=xK bs=1M 

который пропускал бы x * 1024 блоков размером 1M (2 ^ 20). Подробные сведения об обработке устройств см. В dd(1) .

Если вы хотите автоматизировать двоичный поиск, предполагая, что ваш журнал имеет обычный формар <date> [data] вы можете вывести вывод в head -n 2 , проверить дату в начале второй строки (которая – под разумное предположение о «нормальных» длинных линиях – будет полным) и решить, какую половину вы хотите.

Получите размер файла и разделите его на 2. Разделите его на 1024, чтобы получить KiB. (Или 1024 * 1024, чтобы получить MiB и т. Д.)

 ((fs = $(stat -c %s logfile) / 2 / 1024)) 

Пропустить и выполнить поиск

 dd if=logfile bs=1024 skip=$fs | grep blahblah 

Вы можете продолжить это, если файл журнала очень согласован с количеством данных pr. день, добавив значение count= в dd .

 ((cnt = $(stat -c %s logfile) / 5 / 1024)) dd if=logfile bs=1024 skip=$fs count=$cnt | grep blahblah 

Это будет cnt * 1024 байта данных со смещением fs * 1024 байта.

Оберните все это в скрипте и выполните прокладку вне сценария grep, временный файл или что угодно.

Не совсем понятно, что именно вы хотите сделать и что вы имеете в виду под моим «процессом». Для больших файлов моя любимая интерактивная программа less . Он обрабатывает большие файлы без проблем. Он также может пропускать определенный процент, например, используя 30% . Кроме того, вы можете искать с помощью / и ? ,