Установить непосредственно данные членов в скудной разреженной матрице - PullRequest
0 голосов
/ 07 марта 2020

Я создаю большую разреженную матрицу CSR, которая использует довольно много памяти даже в разреженном формате, поэтому я хочу избежать копирования при создании матрицы. Наиболее эффективный способ, который я нашел, - это создание сжатого представления разреженных строк напрямую. Однако инициализатор класса копирует массивы, которые я передаю ему, поэтому я установил непосредственно элементы данных. Пример:

from scipy import sparse
m = sparse.csr_matrix((5,5))
m.data = np.arange(5)
m.indices = np.arange(5)
m.indptr = np.arange(6)

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

Также было бы полезно узнать, могу ли я использовать массивы memmapped без причуд или использовать различные целочисленные типы данных для индексов.

Редактировать:

Принятые ответ показывает, что при правильных типах индексов копирование не происходит. Я проверил __init__ и, даже когда он не копирует indices и indptr, он дважды сканирует оба из них, чтобы найти минимальное и максимальное значения, и фактически ничего не делает, кроме установки data, indices и indptr членов, если входы правильно сформированы, поэтому для производительности я сейчас делаю:

# [...] get shape and data from somewhere
m = sparse.csr_matrix(shape, dtype=data.dtype)
indices = np.empty(..., dtype=m.indices.dtype)
indptr = np.empty(..., dtype=m.indptr.dtype)
# [...] fill indices and indptr
m.data = data
m.indices = indices
m.indptr = indptr
# Possibly also do one or both of the following:
m.has_sorted_indices = True
m.has_canonical_format = True

1 Ответ

1 голос
/ 07 марта 2020

Вот пример создания разреженной матрицы без копирования массивов определений:

In [191]: data=np.arange(5) 
     ...: indices=np.arange(5).astype('int32') 
     ...: indptr=np.arange(6).astype('int32')                                                  
In [192]: M = sparse.csr_matrix((data,indices,indptr))                                         
In [193]: data.__array_interface__['data'], M.data.__array_interface__['data']                 
Out[193]: ((55897168, False), (55897168, False))
In [194]: indices.__array_interface__['data'], M.indices.__array_interface__['data']           
Out[194]: ((70189040, False), (70189040, False))
In [195]: indptr.__array_interface__['data'], M.indptr.__array_interface__['data']             
Out[195]: ((56184432, False), (56184432, False))

https://github.com/scipy/scipy/blob/v1.4.1/scipy/sparse/compressed.py

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

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...