Использование pytables, что более эффективно: scipy.sparse или плотная матрица numpy?

При использовании pytables нет поддержки (насколько я могу судить) для форматов матриц scipy.sparse, поэтому для хранения матрицы мне нужно выполнить некоторое преобразование, например.

def store_sparse_matrix(self):
    grp1 = self.getFileHandle().createGroup(self.getGroup(), 'M')
    self.getFileHandle().createArray(grp1, 'data', M.tocsr().data)
    self.getFileHandle().createArray(grp1, 'indptr', M.tocsr().indptr)
    self.getFileHandle().createArray(grp1, 'indices', M.tocsr().indices)

def get_sparse_matrix(self):
    return sparse.csr_matrix((self.getGroup().M.data, self.getGroup().M.indices, self.getGroup().M.indptr))

Беда в том, что функция get_sparse требует некоторого времени (чтение с диска), и, если я правильно понимаю, еще и требует, чтобы данные поместились в память.

Единственный другой вариант, по-видимому, заключается в преобразовании матрицы в плотный формат (numpy array), а затем обычном использовании pytables. Однако это кажется довольно неэффективным, хотя я полагаю, что, возможно, pytables будет заниматься самим сжатием?


person tdc    schedule 17.01.2012    source источник
comment
Использование обычного массива NumPy, безусловно, потребует, чтобы вся матрица, включая нули, поместилась в памяти. Вы также не сможете использовать разреженность в своих алгоритмах. Но в чем именно заключается ваш вопрос?   -  person Fred Foo    schedule 17.01.2012
comment
@larsmans, но при использовании массива NumPy в сочетании с pytables, насколько я понимаю, он загружается с диска только при необходимости, и поэтому вся матрица не должна помещаться в памяти. Однако для этого требуется, чтобы вся матрица, включая нули, хранилась на диске (и, следовательно, при необходимости читалась/записывалась на диск). Кажется, что это создаст ненужные накладные расходы, когда на самом деле может потребоваться прочитать только несколько значений. Однако без встроенной поддержки scipy.sparse я не вижу, как этого избежать?   -  person tdc    schedule 17.01.2012
comment
Итак, вопрос в том, загрузит ли этот спрос матрицу КСО? Я не могу ответить на этот вопрос, так как не знаю PyTables. Я знаю, что вы можете построить матрицу CSR, поддерживаемую массивами mmap'd...   -  person Fred Foo    schedule 17.01.2012
comment
Вы когда-нибудь находили хорошее решение для этого? Я сталкиваюсь с той же проблемой и почти смирился с тем, что просто конвертирую в плотный формат, чтобы нормально использовать pytables.   -  person Jesse Sherlock    schedule 16.08.2012
comment
@JesseSherlock К сожалению, не совсем. В конце концов мы решили отказаться от pytables, так как он вообще не подходит для разреженных матриц, и для нас было важнее иметь возможность использовать scipy. Решение, которое у нас есть, состоит в том, чтобы сериализовать строки матрицы на диск (фактически mongodb) независимо друг от друга в разреженном формате (индексы столбцов и данные). Таким образом, если строка матрицы изменится, эта строка — это все, что нужно сбросить. Однако это несколько негибко для изменений в столбцах, которые требуют полной очистки (или некоторого кода, вызывающего головную боль...), но это редкое явление в нашем приложении.   -  person tdc    schedule 16.08.2012
comment
Вы имеете дело с одной разреженной матрицей, которая не помещается в оперативную память? Это довольно хардкорно. Тот факт, что вы даже думаете о том, чтобы рассматривать одну и ту же матрицу как плотную, означает, что кто-то из нас двоих что-то здесь упускает.   -  person Eelco Hoogendoorn    schedule 28.12.2013
comment
Что касается инкрементального обновления матрицы на диске; в зависимости от структуры вашей матрицы, хранилище pytables в виде фрагментов может подойти для ваших нужд. Только фрагменты с ненулевыми значениями фактически сохраняются на диск.   -  person Eelco Hoogendoorn    schedule 28.12.2013
comment
Еще одна возможность, которая только что пришла мне в голову, которая должна удовлетворить все ваши потребности, если я правильно их понимаю; вы должны иметь возможность хранить матрицу в формате координат (i, j, data) в pytables. Затем, если вы индексируете столбцы i и j, обновления как строк, так и столбцов с помощью table.where() должны быть очень эффективными, независимо от того, насколько велика ваша матрица.   -  person Eelco Hoogendoorn    schedule 31.12.2013


Ответы (1)


Заимствуя из Хранение разреженной матрицы numpy в HDF5 (PyTables), вы можете маршалировать массив scipy.sparse в формат pytables, используя его атрибуты data, indicies и indptr, которые представляют собой три обычных объекта numpy.ndarray.

person IanSR    schedule 23.01.2014
comment
Проблема с этим подходом заключается в том, что вам придется десериализовать все это, чтобы использовать над ним матричные операции scipy, или написать свой собственный эквивалент, который работает с элементами данных в pytables. - person tdc; 24.01.2014
comment
Также см. мой ответ на вопрос, на который вы ссылаетесь... вы также должны сохранить атрибут shape. - person Pietro Battiston; 03.04.2014