SciPy.sparseのまとめ

2021年12月18日

行列内の値の殆どを0で占めるような行列を疎行列といいます。そんな疎行列のデータを圧縮して効率的に計算を行うseipy.sparseについてまとめていきます。

scipy.sparseの疎行列クラス

csr_matrix 圧縮行格納方式

CSR(Compressed Sparse Row)は行ごとに圧縮を行います。

書き方

csr_matrix( 配列 )

scipy.sparse.csr_matrix 公式

【例】csr_matrixの出力
from scipy.sparse import csr_matrix
 
ary = [[10, 0, 20],
     [0, 30, 40],
     [0, 0, 50]]
 
csr = csr_matrix(ary)
print(csr)
  (0, 0)	10
  (0, 2)	20
  (1, 1)	30
  (1, 2)	40
  (2, 2)	50
csr_matrix解説

例で作成した配列を図にしてみると下記のようなマトリクス図になります。
青文字は(行,列)を表しています。

この図から(行,列)の位置とそれぞれの値が対応しているのが見てとれます。

更に1行目から順番に見ていくと、出力結果の(0,0) 10, (0,2) 20, (1,1) 30と1行目から順に出力されているのが確認できます。

data属性

マトリクスCSRフォーマットのデータ配列を表します。つまり、値そのものを表しています。
結果は行の順で表示されます。

【例】dataの出力
print(csr.data)
[10 20 30 40 50]

indices属性

マトリクスCSRフォーマットのインデックス配列を表します。 indicesは文字通りインデックス(indicesはindexの複数形)を意味しています。

【例】indicesの出力
print(csr.indices)
[0 2 1 2 2]
indices解説

ここで言うインデックスは下記の図の赤丸で囲った数字を指します。

つまり、dataで出力した数字が何列名かを表しており、10なら0、20なら2、という具合にインデックスが設定されています。

行で圧縮するcsrのインデックスは列番号ということになります。

indptr属性

マトリクスCSRフォーマットのインデックスポインタ配列を表します。 ind(インデックス)のptr(ポインタ)ということです。

【例】indptrの出力
print(csr.indptr)
[0 2 4 5]
indptr解説

ind(インデックス)のptr(ポインタ)とは下記の図のようなイメージです。
図では矢印がポインタを表しており、それぞれの色と丸印が対応しているポインタの位置を表しています。

ポインタは1行目、2行目、3行目と進んでいきます。

ポインタが青の位置の時(スタート位置の時)、それ以上値が存在しないので個数は0。
ポインタが赤の位置の時、ポインタ位置よりも上にある値は10と20で2個。
ポインタが緑の位置の時、ポインタ位置よりも上にある値は10と20と30と40で4個。
ポインタが黒の位置の時、ポインタ位置よりも上にある値は10と20と30と40と50で5個。

つまり、ポインタの位置によってそれぞれの数字をカウントしていることになります。

csc_matrix 圧縮列格納方式

CSC(Compressed Sparse Column)は列ごとに圧縮を行います。

書き方

csc_matrix( 配列 )

scipy.sparse.csc_matrix 公式

【例】csc_matrixの出力
from scipy.sparse import csc_matrix

ary = [[10, 0, 20],
     [0, 30, 40],
     [0, 0, 50]]

csc = csc_matrix(ary)
print(csc)
  (0, 0)	10
  (1, 1)	30
  (0, 2)	20
  (1, 2)	40
  (2, 2)	50
csc_matrix解説

例で作成した配列を図にしてみると下記のようなマトリクス図になります。
青文字は(行,列)を表しています。

この図から(行,列)の位置とそれぞれの値が対応しているのが見てとれ、更に1列目から順番に見ていくと、出力結果の(0,0) 10, (1,1) 30, (0,2) 20と1列目から順に出力されているのが確認できます。

data属性

マトリクスのデータ配列で、値そのものを意味します。結果は列の順で表示されます。

【例】dataの出力
print(csc.data)
[10 30 20 40 50]

indices属性

CSCフォーマットのインデックス配列を表します。つまり値の位置を示すインデックスを出力します。

【例】indicesの出力
print(csc.indices)
[0 1 0 1 2]
indices解説

インデックスとは下記の図の赤丸で囲った数字を指します。

つまり、dataで出力した数字が何行目かを表しており、10なら0、30なら1、20なら0、という具合にインデックスが設定されています。

列で圧縮するcscのインデックスは行番号ということになります。

indptr属性

CSCフォーマットのインデックスポインタ配列を表します。

【例】indptrの出力
print(csc.indptr)
[0 1 2 5]
indptr解説

indptr(インデックスポインタ)とは下記の図のようなイメージです。
図では矢印がポインタを表しており、それぞれの色と丸印が対応しているポインタの位置を表しています。

ポインタは1列目、2列名、3列目と進んでいきます。

ポインタが青の位置の時(スタート位置の時)、それ以上値が存在しないので個数は0。
ポインタが赤の位置の時、ポインタ位置よりも左にある値は10のみで1個。
ポインタが緑の位置の時、ポインタ位置よりも左にある値は10と30で2個。
ポインタが黒の位置の時、ポインタ位置よりも左にある値は10と30と20と40と50で5個。

つまり、ポインタの位置によってそれぞれの数字をカウントしていることになります。

lil_matrix 行単位リスト

lil(LInked List)は行ごとの情報(値、インデックス)をlistで保持します。

書き方

lil_matrix( 配列 )

scipy.sparse.lil_matrix 公式

【例】lil_matrixの出力
from scipy.sparse import lil_matrix

ary = [[10, 0, 20],
     [0, 30, 40],
     [0, 0, 50]]

lil = lil_matrix(ary)
print(lil)
  (0, 0)	10
  (0, 2)	20
  (1, 1)	30
  (1, 2)	40
  (2, 2)	50
lil_matrix解説

出力形式はcsr_matrixと同様ですが、再掲しておきます。(行,列)を表しています。

出力結果と1行目を照らし合わせると、(0,0) 10, (0,2) 20、二行目は、(1,1) 30,(1,2) 40となり、値がある場所と出力結果が対応しているのが確認できます。

data属性

マトリクスlilフォーマットのデータ配列を表しています。各行の値をlistで保持しています。

【例】dataの出力
print(lil.data)
[list([10, 20]) list([30, 40]) list([50])]

結果を見ると、1行目の値10,20がlistで所持され、2行目の値30,40がlistで所持され、という具合になっているのが確認出来ると思います。

rows属性

マトリクスlilフォーマットの行インデックス配列を表します。

【例】rowsの出力
print(lil.rows)
[list([0, 2]) list([1, 2]) list([2])]
rows解説

rowsは、行毎のインデックスをlistで保持しています。

図の赤丸と結果を照らし合わせる見ると、1行目が0,2、2行目が1,2、3行目が2、とそれぞれ対応しているのが確認できます。行単位のリストなのでインデックスは何列目かを表しています。

coo_matrix 疎マトリクス

COOrdinate(座標)は座標フォーマットの疎なマトリクスを表します。つまり、行ごとまたは列ごとのインデックスを保持します。

書き方

coo_matrix( 配列 )

scipy.sparse.coo_matrix 公式

【例】coo_matrixの出力
from scipy.sparse import coo_matrix

ary = [[10, 0, 20],
     [0, 30, 40],
     [0, 0, 50]]

coo = coo_matrix(ary)
print(coo)
  (0, 0)	10
  (0, 2)	20
  (1, 1)	30
  (1, 2)	40
  (2, 2)	50

出力結果はcsr_matrixと同様に、(行,列) 値、を表しています。

data属性

マトリクスCOOフォーマットのデータ配列を表します。csr_matrixと同様に値そのものを表しています。

【例】dataの出力
print(coo.data)
[10 20 30 40 50]

row属性

マトリクスCOOフォーマットの行インデックス配列を表します。つまり行番号を出力します。

【例】rowの出力
print(coo.row)
[0 0 1 1 2]
row解説

row(行)は、下記の図の赤丸で囲った数字を指します。

出力結果と赤丸の数字を照らし合わせてみると、各行番号を表していることが確認できます。

col属性

マトリクスCOOフォーマットの列インデックス配列を表します。つまり列番号を出力します。

【例】colの出力
print(coo.col)
[0 2 1 2 2]
col解説

col(列)は、下記の図の赤丸で囲った数字を指します。

出力結果と赤丸の数字を照らし合わせてみると、各列番号を表していることが確認できます。

hstack 水平方向の連結

hstack(horizontal stack)は疎のマトリクス(行列)を水平方向に連結します。

Numpyにもhstackがあります。

書き方

hstack([ 配列1, 配列2 ])

scipy.sparse.hstack 公式

【例】hstackの出力
from scipy.sparse import coo_matrix, hstack

ary1 = [[10, 0, 20],
     [0, 30, 40],
     [0, 0, 50]]

ary2 = [[60, 0, 70],
     [0, 80, 90],
     [0, 0, 100]]

coo1 = coo_matrix(ary1)
coo2 = coo_matrix(ary2)

hs = hstack([coo1,coo2]).toarray()
print(hs)
[[ 10   0  20  60   0  70]
 [  0  30  40   0  80  90]
 [  0   0  50   0   0 100]]

出力結果より、それぞれの配列ary1,ary2の一行目を見てみると、[10,0,20]と[60,0,70]が[10,0,20,60,0,70]と連結されているのが確認できます。

SciPy

Posted by Bright_Noah