如何将scipy csr_matrix转换回行、列和数据列表?

7

我有一个scipy csr_matrix,根据文档的规定创建方式如下:

import numpy as np
from scipy.sparse import csr_matrix
row = np.array([0, 0, 1, 2, 2, 2])
col = np.array([0, 2, 2, 0, 1, 2])
data = np.array([1, 2, 3, 4, 5, 6])
mtr = csr_matrix((data, (row, col)))
mtr.toarray()
array([[1, 0, 2],
       [0, 0, 3],
       [4, 5, 6]])

如何高效地将矩阵mtr转换回最初的三个列表row, coldata

2个回答

7

正如您在评论中提到的,您可以通过访问data属性来获取数据。要获取行和列,您可以将数组转换为COO格式,并访问datarowcol属性:

这是您的数组mtr

In [11]: mtr
Out[11]: 
<3x3 sparse matrix of type '<class 'numpy.int64'>'
    with 6 stored elements in Compressed Sparse Row format>

In [12]: mtr.A
Out[12]: 
array([[1, 0, 2],
       [0, 0, 3],
       [4, 5, 6]], dtype=int64)

将数据转换为COO格式,并访问datarowcol属性。

In [13]: c = mtr.tocoo()

In [14]: c.data
Out[14]: array([1, 2, 3, 4, 5, 6], dtype=int64)

In [15]: c.row
Out[15]: array([0, 0, 1, 2, 2, 2], dtype=int32)

In [16]: c.col
Out[16]: array([0, 2, 2, 0, 1, 2], dtype=int32)

3

只需调用 my_csr_matrix.nonzero(),然后进行索引即可。

代码:

import numpy as np
from scipy.sparse import csr_matrix
row = np.array([0, 0, 1, 2, 2, 2])
col = np.array([0, 2, 2, 0, 1, 2])
data = np.array([1, 2, 3, 4, 5, 6])
mtr = csr_matrix((data, (row, col)))

print(mtr.todense())

rows, cols = mtr.nonzero()
data = mtr[rows, cols]

print(rows, cols, data)

输出:

[[1 0 2]
 [0 0 3]
 [4 5 6]]
[0 0 1 2 2 2] [0 2 2 0 1 2] [[1 2 3 4 5 6]]

谢谢。另外我发现获取数据只需使用 mtr.data - Sergey Zakharov
1
是的,我对 .data 的顺序也不确定,但似乎那样做也可以(而且更快)。 - sascha
1
查看 mtr.nonzero 代码。它将 mtr 转换为 coo,并返回行和列属性(但会进行额外的 data!=0 测试,以防在创建矩阵后将某些值设置为 0)。 - hpaulj
看看这段代码。它从返回的数组中删除那些额外的 0,但不修改原始矩阵。有一个单独的方法用于清除零(csr_matrix.eliminate_zeros)。每个方法的“doc”页面都有一个[source]链接。 - hpaulj
@hpaulj 抱歉,我在这个话题上是新手,不太习惯阅读源代码。删除零可能会成为一个问题,因为我故意在一个矩阵的最后一列添加了一个零,以使其形状与我使用的其他矩阵对齐,因为我需要对它们进行许多逐点操作。您有什么建议来处理它? - Sergey Zakharov
显示剩余2条评论

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接