2012-11-12 13 views
16

SciPy Sparse Matrix tutorial jest bardzo dobra - ale w rzeczywistości pozostawia sekcję o krojeniu un (der) opracowaną (nadal w formie konspektu - patrz sekcja: "Obsługa rzadkich matryc").Krojenie rzadkich matryc w Scipy - które typy działają najlepiej?

Spróbuję i zaktualizuję samouczek, po udzieleniu odpowiedzi na to pytanie.

Mam dużą macierz rzadką - obecnie w formacie dok_matrix.

import numpy as np 
from scipy import sparse 
M = sparse.dok_matrix((10**6, 10**6)) 

Dla różnych metod chcę być w stanie wycinać kolumny, a dla innych chcę wycinać wiersze. Idealnie chciałbym użyć zaawansowanego indeksowania (czyli wektor logiczna, bool_vect), z którym pokroić rzadki macierzy M - podobnie jak w:

bool_vect = np.arange(10**6)%2 # every even index 
out = M[bool_vect,:]   # Want to select every even row 

lub

out = M[:,bool_vect] # Want to select every even column 

pierwsze, dok_matrices nie obsługują to - ale myślę, że to działa (powoli), jeśli najpierw rzucam na lil_matrices, poprzez sparse.lil_matrix(M)

O ile mogę zebrać z samouczka - do wycinania kolumn chcę użyć CSC i wycinać wiersze, które chcę wycinanie CSR. Więc to znaczy mam rzucać matrycę M poprzez:

M.tocsc()[:,bool_vect] 

lub

M.tocsr()[bool_vect,:] 

jestem trochę zgadywania tutaj i mój kod jest powolny ze względu na niego. Każda pomoc od kogoś, kto rozumie, jak to działa, byłaby doceniona. Z góry dziękuję.

Jeśli się okaże, że nie powinienem indeksować mojej macierzy za pomocą tablicy boolowskiej, ale raczej listę liczb całkowitych (indeksów) - to też jest coś, co chętnie znajdę. Którakolwiek jest bardziej wydajna.

Wreszcie - jest to duża matryca, więc punkty bonusowe, jeśli może się to zdarzyć w miejscu/z transmisją.

Odpowiedz

31

OK, więc jestem całkiem pewny, że "właściwy" sposób to zrobić: jeśli kroisz kolumny, użyj tocsc() i plasterka używając listy/tablicy liczb całkowitych. Wektory boolowskie nie radzą sobie z rzadkimi macierzami - tak jak robi to z ndarrays w numpy. Co oznacza, że ​​odpowiedź jest.

indices = np.where(bool_vect)[0] 
out1 = M.tocsc()[:,indices] 
out2 = M.tocsr()[indices,:] 

Ale pytanie: czy to najlepszy sposób? Czy to jest na miejscu?

W praktyce wygląda na to, że dzieje się to na miejscu - i jest znacznie szybsze niż wcześniejsze próby (za pomocą lil_matrix).

+0

Jeśli 'M' jest formatem, który nie ma indeksowania (' coo' lub 'dok'), to ta konwersja jest właściwa. Ale jeśli 'M' jest już' csr' przełączenie na 'csc' po prostu na indeksowanie kolumn może nie być tego warte. Indeksowanie "rzadkie" to skomplikowana sprawa. – hpaulj

Powiązane problemy