pyarrow.parquet.write_to_dataset () очень медленно при использовании partition_cols

Я балуюсь паркетными напильниками, чтобы понять, подходят ли они для моих целей. Для этого я загружаю набор данных из файла csv и сохраняю его как набор данных паркета:

import pandas as pd          # version 0.25
import pyarrow as pa         # version 0.15
import pyarrow.parquet as pq

df = pd.read_csv('my.csv')

df_table = pa.Table.from_pandas(df)
pq.write_to_dataset(df_table, root_path='my.parquet')

Это работает нормально и довольно быстро (~ 1 минута). Однако, когда я пытаюсь написать такой секционированный набор данных паркета,

pq.write_to_dataset(df_table, root_path='my.parquet', partition_cols=['id'])

на это уходит больше получаса. Это кажется странным. Я попытался установить столбец id в качестве индекса, но это не сильно изменилось. Я что-то упускаю?

Немного предыстории файла: ~ 5 миллионов строк, 9 столбцов. Столбец id содержит ~ 330 000 различных значений. Разве это плохая идея - разбивать набор данных на такие маленькие части?


Я новичок в Python (использую версию 3.6.4), поэтому не уверен, что предоставил всю необходимую информацию. Прокомментируйте, если чего-то не хватает.


РЕДАКТИРОВАТЬ: Я обнаружил, что в моем случае меньшее количество больших фрагментов выполняется быстрее. Это приводит к вопросу об оптимальном размере блока. Где я могу найти информацию об этом?


person der_grund    schedule 19.11.2019    source источник


Ответы (1)


При ~ 15 (5 миллионов / 330 КБ) строк на файл, да, использовать паркет для таких небольших файлов - плохая идея. Метаданные в паркете связаны с накладными расходами, и степень сжатия будет ограничена. На основе документации по паркету размер группы строк ~ 512-1024 МБ является предпочтительным, но это из-за HDFS. Таким образом, для разных сценариев хранения могут потребоваться разные размеры. В общем, это, вероятно, не имеет смысла для файлов размером менее 10 мегабайт.

person Micah Kornfield    schedule 20.11.2019
comment
Спасибо за ссылку на документацию. Должно быть, я это раньше не замечал. Итак, мой вывод по работе с паркетными файлами на локальном компьютере: выберите размер блока как можно больше, но достаточно мал, чтобы уместить в ОЗУ столько блоков, сколько ядер у вас есть. Имеет ли это смысл? - person der_grund; 20.11.2019
comment
Это кажется хорошим практическим правилом, но я думаю, что это, вероятно, зависит от рабочей нагрузки (например, сколько столбцов вы читаете за раз). - person Micah Kornfield; 21.11.2019