稀疏矩阵-sparsep
1
|
from scipy import sparse
|
稀疏矩阵的储存形式
在科学与工程领域中求解线性模型时经常出现许多大型的矩阵,这些矩阵中大部分的元素都为0,被称为稀疏矩阵。用NumPy的ndarray数组保存这样的矩阵,将很浪费内存,由于矩阵的稀疏特性,可以通过只保存非零元素的相关信息,从而节约内存的使用。此外,针对这种特殊结构的矩阵编写运算函数,也可以提高矩阵的运算速度。
scipy.sparse库中提供了多种表示稀疏矩阵的格式,每种格式都有不同的用处,其中dok_matrix和lil_matrix适合逐渐添加元素。
dok_matrix从dict继承,它采用字典保存矩阵中不为0的元素:字典的键是一个保存元素(行,列)信息的元组,其对应的值为矩阵中位于(行,列)中的元素值。显然字典格式的稀疏矩阵很适合单个元素的添加、删除和存取操作。通常用来逐渐添加非零元素,然后转换成其它支持快速运算的格式。
1
2
3
4
|
a = sparse.dok_matrix(( 10 , 5 ))
a[ 2 : 5 , 3 ] = 1.0 , 2.0 , 3.0
print a.keys()
print a.values()
|
1
2
|
[( 2 , 3 ), ( 3 , 3 ), ( 4 , 3 )]
[ 1.0 , 2.0 , 3.0 ]
|
lil_matrix使用两个列表保存非零元素。data保存每行中的非零元素,rows保存非零元素所在的列。这种格式也很适合逐个添加元素,并且能快速获取行相关的数据。
1
2
3
4
5
6
|
b = sparse.lil_matrix(( 10 , 5 ))
b[ 2 , 3 ] = 1.0
b[ 3 , 4 ] = 2.0
b[ 3 , 2 ] = 3.0
print b.data
print b.rows
|
1
2
|
[[] [] [ 1.0 ] [ 3.0 , 2.0 ] [] [] [] [] [] []]
[[] [] [ 3 ] [ 2 , 4 ] [] [] [] [] [] []]
|
coo_matrix采用三个数组row、col和data保存非零元素的信息。这三个数组的长度相同,row保存元素的行,col保存元素的列,data保存元素的值。coo_matrix不支持元素的存取和增删,一旦创建之后,除了将之转换成其它格式的矩阵,几乎无法对其做任何操作和矩阵运算。
coo_matrix支持重复元素,即同一行列坐标可以出现多次,当转换为其它格式的矩阵时,将对同一行列坐标对应的多个值进行求和。在下面的例子中,(2, 3)对应两个值:1和10,将其转换为ndarray数组时这两个值加在一起,所以最终矩阵中(2, 3)坐标上的值为11。
许多稀疏矩阵的数据都是采用这种格式保存在文件中的,例如某个CSV文件中可能有这样三列:“用户ID,商品ID,评价值”。采用numpy.loadtxt或pandas.read_csv将数据读入之后,可以通过coo_matrix快速将其转换成稀疏矩阵:矩阵的每行对应一位用户,每列对应一件商品,而元素值为用户对商品的评价。
1
2
3
4
5
6
|
row = [ 2 , 3 , 3 , 2 ]
col = [ 3 , 4 , 2 , 3 ]
data = [ 1 , 2 , 3 , 10 ]
c = sparse.coo_matrix((data, (row, col)), shape = ( 5 , 6 ))
print c.col, c.row, c.data
print c.toarray()
|
1
2
3
4
5
6
|
[ 3 4 2 3 ] [ 2 3 3 2 ] [ 1 2 3 10 ]
[[ 0 0 0 0 0 0 ]
[ 0 0 0 0 0 0 ]
[ 0 0 0 11 0 0 ]
[ 0 0 3 0 2 0 ]
[ 0 0 0 0 0 0 ]]
|
个人操作中选择,coo_matrix 选在因为涉及稀疏矩阵运算,但是如果不用其他形式存储则复杂度太高(时间和空间)1000*1000的matrix大约话2h,也是要命了。无奈想到了Pajek软件中数据的输入格式三元组:
所以想到将自己的数据处理成类似的三元组!
即“matrix矩阵”—>"tuple三元组"—>"sparseMatrix2tuple"—>"scipy.sparse"
感谢阅读,希望能帮助到大家,谢谢大家对本站的支持!
原文链接:https://my.oschina.net/u/1462678/blog/908403