关于Pytorch和Numpy中的稀疏矩阵sparse的知识点

Pytorch和Numpy中的稀疏矩阵sparse

  • 0 稀疏矩阵类别
    • 0.1 coo_matrix
    • 0.2 dok_matrix
    • 0.3 csr_matrix
    • 0.4 csc_matrix
    • 0.5 bsr_matrix
    • 0.6 bsc_matrix
    • 0.7 lil_matrix
    • 0.8 dia_matrix
  • 1 pytorch中的稀疏矩阵
    • 1.1 to_sparse()
    • 1.2 to_sparse_csr()
    • 1.3 sparse_coo_tensor()
    • 1.4 sparse_csr_tensor()
    • 1.5 sparse.sum()
    • 1.6 sparse.mm()
  • 2 numpy中的稀疏矩阵
  • 参考博文及感谢

写在前面,pytorch和numpy都有对稀疏矩阵的操作,最大的区别在于pytorch可以通过GPU进行加速;不过现在numpy这边也推出了智能AI来加速对稀疏矩阵的运算;下面就稍微梳理一下关于稀疏矩阵的相关知识点,以飨诸君~

0 稀疏矩阵类别

不管是pytorch还是numpy,他们对稀疏矩阵的处理都是根据稀疏矩阵类别来的;所以先简单介绍稀疏矩阵的类别,这里网上已经有大量针对这些类别的详细解释说明,我这边就做引用:

SciPy 中不同稀疏矩阵存储方式介绍 (这个博客经常更换地址,而且加载不出图;但是是原创,所以贴出来);
不同稀疏矩阵存储方式介绍(这是对上面博客的CSDN转载,可看图)。

0.1 coo_matrix

对角存储矩阵(Coordinate Matrix)的简称
优:
能与CSR / CSC格式的快速转换

(tobsr()、tocsr()、to_csc()、to_dia()、to_dok()、to_lil()

缺:
不支持切片和算术运算操作

0.2 dok_matrix

按键字典矩阵(Dictionary of Keys Matrix)的简称
优:
对于递增的构建稀疏矩阵很高效,比如定义该矩阵后,想进行每行每列更新值,可用该矩阵。
可以高效访问单个元素,只需要O(1)
缺:
不允许重复索引(coo中适用),但可以很高效的转换成coo后进行重复索引

0.3 csr_matrix

压缩稀疏行矩阵(Compressed Sparse Row Matrix )的简称
优:
高效的稀疏矩阵算术运算
快速地矩阵矢量积运算

缺:
转换到稀疏结构代价较高(可以考虑LIL,DOK)

0.4 csc_matrix

压缩稀疏列矩阵(Compressed Sparse Column Matrix )的简称
优缺:
同上

0.5 bsr_matrix

分块压缩稀疏行矩阵(Block Sparse Row Matrix )的简称
优:
更适合于适用于具有密集子矩阵的稀疏矩阵

0.6 bsc_matrix

分块压缩稀疏列矩阵(Block Sparse Column Matrix )的简称
优:
更适合于适用于具有密集子矩阵的稀疏矩阵

0.7 lil_matrix

链表矩阵(Linked List Matrix )的简称
优:
适合递增的构建成矩阵
转换成其它存储方式很高效
支持灵活的切片
缺:
算术操作,列切片,矩阵向量内积操作慢(考虑用coo)

0.8 dia_matrix

对角存储矩阵(Diagonal Matrix)的简称

1 pytorch中的稀疏矩阵

先上官网开发文档镇楼TORCH.SPARSE 1.13 开发文档。
值得说明的是目前pytorch 只支持 COO, CSR, CSC, BSR, 和 BSC五种矩阵,可以用numpy转完在用pytorch。

这里首先讲pytorch而不是numpy的原因是pytorch确实比numpy快,具体看这里这个测试numpy, torch.spmm和torch.spmm 速度测试;
常用的方法有如下

1.1 to_sparse()

a = torch.tensor([[0, 2.], [3, 0]])
a.to_sparse()

官网有例子,不再重复造轮子;

1.2 to_sparse_csr()

1.3 sparse_coo_tensor()

1.4 sparse_csr_tensor()

crow_indices = torch.tensor([0, 2, 4])
col_indices = torch.tensor([0, 1, 0, 1])
values = torch.tensor([1, 2, 3, 4])
csr = torch.sparse_csr_tensor(crow_indices, col_indices, values, dtype=torch.float64)
csr
"""
tensor(crow_indices=tensor([0, 2, 4]),
      col_indices=tensor([0, 1, 0, 1]),
      values=tensor([1., 2., 3., 4.]), size=(2, 2), nnz=4,
      dtype=torch.float64)
"""
csr.to_dense()
"""
tensor([[1., 2.],
        [3., 4.]], dtype=torch.float64)
"""

1.5 sparse.sum()

1.6 sparse.mm()

这里提一句,torch.sparse.mm()和torch.spmm()是一样的,映射到的底层函数函数一样;具体可看这个numpy, torch.spmm和torch.spmm 稀疏矩阵乘法 测试;

2 numpy中的稀疏矩阵

照例搬出官方文档镇楼,Sparse matrices 1.11.4 官方文档
numpy是高性能科学计算和数据分析的基础包,其对稀疏矩阵的操作主要依赖于scipy开发包。

此处仍然引开篇的博客SciPy 中不同稀疏矩阵存储方式介绍

关于使用智能AI来加速对稀疏矩阵的运算,可参考此链接一行代码加速 sklearn 运算上千倍
原汁原味的官方 -->Intel® Extension for Scikit-learn

PS:如果对numpy中的方法不熟,可以看这篇博客NumPy:数组批量计算

再贴一个numpy稀疏矩阵转pytorch的代码:

def sparse_mx_to_torch_sparse_tensor(sparse_mx):
    """Convert a scipy sparse matrix to a torch sparse tensor."""
    if type(sparse_mx) != sp.coo_matrix:
        sparse_mx = sparse_mx.tocoo().astype(np.float32)
    indices = torch.from_numpy(
        np.vstack((sparse_mx.row, sparse_mx.col)).astype(np.int64))
    values = torch.from_numpy(sparse_mx.data).float()
    shape = torch.Size(sparse_mx.shape)
    return torch.sparse.FloatTensor(indices, values, shape)

参考博文及感谢

部分内容参考以下链接,这里表示感谢 Thanks♪(・ω・)ノ
参考博文1 Pytorch 关于稀疏矩阵 1.13 官方开发文档
https://pytorch.org/docs/1.13/sparse.html?highlight=sparse#module-torch.sparse
参考博文2 Numpy 关于稀疏矩阵 Sparse matrices 1.11.4 官方文档
https://docs.scipy.org/doc/scipy/reference/sparse.html
参考博文3 SciPy 中不同稀疏矩阵存储方式介绍
https://dreamhomes.github.io/posts/202012311027/
参考博文4 不同稀疏矩阵存储方式介绍
https://blog.csdn.net/DreamHome_S/article/details/111994423
参考博文5 numpy, torch.spmm和torch.spmm 稀疏矩阵乘法测试
https://github.com/rusty1s/pytorch_sparse/issues/356
参考博文6 一行代码加速 sklearn 运算上千倍
https://blog.csdn.net/dQCFKyQDXYm3F8rB0/article/details/125382907
参考博文7 Intel® Extension for Scikit-learn

你可能感兴趣的:(python,Pytorch,机器学习,pytorch,numpy,矩阵)