случайный поиск в одном файловом архиве 7z - PullRequest
2 голосов
/ 25 октября 2011

Возможно ли сделать произвольный доступ (много запросов) к очень огромному файлу, сжатому 7zip?

Исходный файл очень большой (999 ГБ xml), и я не могу сохранить его в распакованном формате (у меня не так много свободного места). Итак, если формат 7z позволяет получить доступ к среднему блоку без разархивирования всех блоков перед выбранным, я могу построить индекс начала блока и соответствующие исходные смещения файла.

Заголовок моего архива 7z

37 7A BC AF 27 1C 00 02 28 99 F1 9D 4A 46 D7 EA  // 7z archive version 2;crc; n.hfr offset
00 00 00 00 44 00 00 00 00 00 00 00 F4 56 CF 92  // n.hdr offset; n.hdr size=44. crc
00 1E 1B 48 A6 5B 0A 5A 5D DF 57 D8 58 1E E1 5F
71 BB C0 2D BD BF 5A 7C A2 B1 C7 AA B8 D0 F5 26
FD 09 33 6C 05 1E DF 71 C6 C5 BD C0 04 3A B6 29

ОБНОВЛЕНИЕ: архиватор 7z сообщает, что этот файл содержит один блок данных, сжатый по алгоритму LZMA. Скорость распаковки при тестировании составляет 600 МБ / с (из распакованных данных), используется только одно ядро ​​ЦП.

Ответы [ 4 ]

2 голосов
/ 25 октября 2011

Это технически возможно, но если ваш вопрос «позволяет ли это доступный в настоящее время двоичный инструмент командной строки 7zip», ответ, к сожалению, нет. Лучшее, что он позволяет, - это независимое сжатие каждого файла в архив, что позволяет файламбыть извлеченным напрямую. Но так как вы хотите сжать один (огромный) файл, этот прием не сработает.

Боюсь, единственный способ состоит в том, чтобы разделить файл на небольшие блоки и скормитьих к кодировщику LZMA (входит в LZMA SDK). К сожалению, это требует некоторых навыков программирования.

Примечание: здесь можно найти технически неполный, но тривиальный алгоритм сжатия. Основная программа делает именно то, что вы ищете:Разрежьте исходный файл на маленькие блоки и подайте их один за другим в компрессор (в данном случае, LZ4). Затем декодер выполняет обратную операцию. Он может легко пропустить все сжатые блоки и перейти прямо к тому, который вы хотитеполучить. http://code.google.com/p/lz4/source/browse/trunk/lz4demo.c

1 голос
/ 25 октября 2011

Как насчет этого:

Концепция: поскольку вы в основном читаете только один файл, индексируйте .7z по блокам.

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

записать индекс в какое-то хранилище O (log n). Для доступа извлеките номер блока и его смещение, извлеките блок и найдите элемент. стоимость связана с извлечением одного блока (или очень немногих) и поиском строки в этом блоке.

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

ЧЕРН: Вы в основном постулировали это в своем вопросе ... кажется, что лучше прочитать вопрос, прежде чем ответить ...

0 голосов
/ 03 февраля 2019

Только для использования:

7z e myfile_xml.7z -so | sed [something] 

Пример получения строки 7:

7z e myfile_xml.7z -so | sed -n 7p

0 голосов
/ 05 июня 2014

7z архиватор сообщает, что этот файл содержит один блок данных, сжатый по алгоритму LZMA.

Какая команда 7z / xz обнаружила, что это один сжатый блок или нет?Будет ли 7z создавать многоблочный (многопотоковый) архив при использовании нескольких потоков?

Исходный файл очень большой (999 ГБ xml)

Хорошая новость: Википедия перешла на многопоточностьархивы для его дампов (по крайней мере, для enwiki): http://dumps.wikimedia.org/enwiki/

Например, самый последний дамп, http://dumps.wikimedia.org/enwiki/20140502/ имеет многопоточный bzip2 (с отдельным индексом "offset: export_article_id: article_name"), идамп 7z хранится во многих архивах sub-GB с ~ 3k (?) статьями на архив:

Статьи, шаблоны, описания медиа / файлов и первичные мета-страницы в нескольких потоках bz2,100 страниц на поток

enwiki-20140502-pages-articles-multistream.xml.bz2 10.8 GB
enwiki-20140502-pages-articles-multistream-index.txt.bz2 150.3 MB

Все страницы с полной историей редактирования (.7z)

enwiki-20140502-pages-meta-history1.xml-p000000010p000003263.7z 213.3 MB
enwiki-20140502-pages-meta-history1.xml-p000003264p000005405.7z 194.5 MB
enwiki-20140502-pages-meta-history1.xml-p000005406p000008209.7z 216.1 MB
enwiki-20140502-pages-meta-history1.xml-p000008210p000010000.7z 158.3 MB
enwiki-20140502-pages-meta-history2.xml-p000010001p000012717.7z 211.7 MB
 .....
enwiki-20140502-pages-meta-history27.xml-p041211418p042648840.7z 808.6 MB

Я думаю, мы можем использовать индекс bzip2 для оценки идентификатора статьи даже для 7zдампов, а затем нам просто нужен архив 7z с правильным диапазоном (..p first_id p last_id .7z).stub-meta-history.xml тоже может помочь.

FAQ по дампам: http://meta.wikimedia.org/wiki/Data_dumps/FAQ

...