Есть ли способ получить представление в стиле numpy для фрагмента массива, хранящегося в файле hdf5?

Мне нужно работать с большими трехмерными кубами данных. Я хочу сохранить их в файлах HDF5 (используя h5py или, возможно, pytables). Я часто хочу провести анализ только части этих кубов. Этот раздел слишком велик для хранения в памяти. Я хотел бы иметь представление в стиле numpy для интересующего меня фрагмента без копирования данных в память (аналогично тому, что вы могли бы сделать с numpy memmap). Это возможно? Насколько мне известно, выполняя срез с использованием h5py, вы получаете массив numpy в памяти.

Меня спросили, зачем мне это делать, ведь в какой-то момент данные все равно должны поступать в память. Мой код по необходимости уже запускал по частям данные из этих кубов, втягивая небольшие биты в память за раз. Эти функции будут самыми простыми, если они просто перебирают все переданные им наборы данных. Если бы у меня было представление данных на диске, я бы просто мог передать это представление этим функциям без изменений. Если у меня нет представления, мне нужно написать все мои функции так, чтобы они выполняли итерацию только по интересующему нас фрагменту. Это усложнит код и повысит вероятность человеческой ошибки во время анализа.

Есть ли способ просмотреть данные на диске без копирования в память?


person Caleb    schedule 06.01.2015    source источник
comment
Вы слышали о пандах. Это может быть очень полезно при чтении / записи Магазин HDF5?   -  person wflynny    schedule 06.01.2015
comment
Это продолжение моего предыдущего вопроса: stackoverflow.com/q/27710245/1361752   -  person Caleb    schedule 06.01.2015
comment
Да, я хорошо знаком с пандами DataFrames (хотя и не столько с их 3D-функциями). Однако это в основном работает в памяти, верно? Я знаю, что вы можете использовать pytables для копирования таблиц в файлы hdf5. Есть ли способ использовать это для нужной мне функциональности? Кроме того, я думаю, что pandas обычно предоставляет типы данных высокого уровня для табличных данных. Разве для простых массивов это не излишество? Тем не менее, если он делает то, что мне нужно, я с радостью им воспользуюсь.   -  person Caleb    schedule 06.01.2015
comment
Я перечитал ваш пост более внимательно, и для ясности: желаемые фрагменты вашего хранилища данных все еще слишком велики для хранения в памяти, верно? Или вы берете прямоугольный срез куба, а затем разрезаете его дальше? Однако позвольте мне провести небольшое исследование, я знаю, что pandas изначально поддерживает чтение с фрагментами hdf5, что, возможно, может упростить ваш рабочий процесс.   -  person wflynny    schedule 06.01.2015
comment
По сути, я часто нацеливаю весь анализ на подмножество полного куба данных. Однако это подмножество слишком велико для заполнения памяти. Один рабочий процесс, который приходит мне на ум, заключается в том, что я могу скопировать подмножество в новый временный файл и работать с ним.   -  person Caleb    schedule 07.01.2015
comment
Вам наверняка понадобится что-то вроде ломтиков от ломтика.   -  person Trilarion    schedule 21.12.2015
comment
Если вам нужно все подмножество для работы вашей обработки, и это подмножество не помещается в памяти, тогда я не понимаю, как вы можете справиться с этим, не обновляя свою обработку для работы с подмножеством подмножества. Кроме того, h5py поддерживает numpy-подобную нарезку, которая должна работать через выделение гиперпластинок, но я недостаточно знаю о ваших данных, чтобы сказать, достаточно ли этого.   -  person somada141    schedule 05.06.2018
comment
Для меня это звучит так, как будто вы ищете dask массивы (хотя я никогда не работал с ними для серьезных приложений, я должен сказать). Он разработан, среди прочего, для того, что вы описываете: данные слишком велики, чтобы поместиться в памяти, и интегрируются с хорошо известными инструментами, такими как pandas и numpy. см. основной веб-сайт: dask.pydata.org/en/latest/docs.html и как создавать массивы dask, также из hfd5: dask.pydata.org/ ru / latest / array-creation.html. По крайней мере, в своих документах они пишут: изменяет ограничение по пространству с «умещается в памяти» на «умещается на диске».   -  person SpghttCd    schedule 21.06.2018
comment
+1 для dask.array. Это решает проблему OP. Я использовал их для массивов из памяти без каких-либо изменений в моем коде numpy.   -  person evamicur    schedule 19.08.2018


Ответы (2)


Одна из возможностей - создать генератор, который генерирует элементы среза один за другим. Когда у вас есть такой генератор, вы можете передать его в существующий код и выполнять итерацию через генератор как обычно. Например, вы можете использовать цикл for в генераторе так же, как вы можете использовать его в срезе. Генераторы не хранят все свои значения сразу, они «генерируют» их по мере необходимости.

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

Предполагая, что ваши срезы (возможно, многомерные) эквивалентны кубоидам, вы можете генерировать координаты, используя вложенные _1 _-_ 2_ циклы или применяя product() из _ 4_ для ранжирования объектов.

person IFcoltransG    schedule 24.02.2019

Неизбежно не копировать этот раздел набора данных в память. Причина в том, что вы запрашиваете весь раздел, а не только его небольшую часть. Следовательно, его нужно скопировать полностью.

Итак, поскольку h5py уже позволяет вам использовать наборы данных HDF5 так же, как массивы NumPy, вам придется изменить свой код, чтобы запрашивать только те значения в наборе данных, которые вам сейчас нужны.

person 1313e    schedule 03.05.2019