大型稀疏矩阵分解

Posted

技术标签:

【中文标题】大型稀疏矩阵分解【英文标题】:Large Sparse Matrix Factorization 【发布时间】:2015-03-01 15:48:34 【问题描述】:

如何在尺寸极其稀疏的矩阵(例如 70000 x 70000)上运行 svdnmf?该矩阵的稀疏版本可以存储为磁盘上小于 700M 的二进制文件。我是否可以将其分解为稀疏格式(如磁盘上的文件或可存储在内存中)而不重构整个矩阵,而这将无法存储在内存中(甚至难以存储在磁盘上)?

我知道 R 中有 irlbapython 中有 sklearnpymf >。但似乎他们需要重建矩阵? svd 的问题是我无法保存矩阵 S,V 和 D,但是如果我指定一个 K 并且只保存矩阵 S_k, V_k 和D_k对应k-最大特征值?而对于nmf,我想将其分解为rank = 100的W,可以存储在内存中。

如果有某些方法可以做到这一点,计算 svdnmf 的预期时间是多少?任何帮助将不胜感激!

【问题讨论】:

Matrixm2 <- Matrix(0, nrow = 7*10^4, ncol = 7*10^4, sparse = TRUE) 仅是281632 bytes @Khashaa 谢谢!我不熟悉 R。那么我可以在 R 中像这样 svd 稀疏矩阵吗?尤其要考虑矩阵 S 和 D 可能是密集的。 SVD for sparse matrix in R的可能重复 @Floo0 谢谢!我检查了链接,但在那个问题中我没有看到矩阵的实际大小。似乎 irlba 适用于 svd (虽然我还没有尝试过)。但是 R 是否将 S 和 D 保存在内存中?此外,R中是否有任何方法适用于NMF? 我看了irlba的文档。它允许指定对限制计算有用的所需奇异向量的数量。至少对于 svd,irlba 似乎还可以。 【参考方案1】:

您可以尝试使用rARPACK 包,它提供了适用于稀疏矩阵的svds() 函数,并且只允许您检索少数奇异值/向量。

有关示例,请参阅README 页面。

【讨论】:

您知道rARPACK irlba 相比如何吗? 我会说他们使用类似的算法,但rARPACK 是使用 C++ 编写的,以避免 R 代码的一些开销。【参考方案2】:

是的,我只是为此目的编写了RcppML R RcppEigen 包。这是我所知道的稀疏矩阵最快的 NMF 实现。

GitHub:github.com/zdebruine/RcppML

install.packages("RcppML")
devtools::install_github("zdebruine/RcppML")

您没有说您的矩阵有多稀疏,但根据您引用的文件大小,我猜测它可以在 HPC 上以非常好的容差在 1-5 分钟内分解。

我一直在使用 RcppML::nmf 在 HPC 上几分钟内将数百万个单细胞的数据集分解为 15,000 个基因(95% 稀疏)。它几乎与等效的 irlba 一样快。

RcppML::nmf 中,R 矩阵确实需要加载,但不会在内存中再次复制(设置update_in_place = TRUE 以避免转置并将该副本存储在内存中)。许多实现(包括python中的实现)创建矩阵的副本是正确的。此外,任何使用 RcppArmadillo 或 RcppEigen 的 R 包都可能使用 arma::SpMatEigen::SparseMatrix Rcpp 类,这需要深拷贝。在 700MB 时,您应该能够将矩阵保存在内存中,或者仅使用 HPC。

我知道的下一个最佳算法是rsparse::WRMF R 包。它也非常好,但是将 R 向量浅拷贝到犰狳向量中。

【讨论】:

以上是关于大型稀疏矩阵分解的主要内容,如果未能解决你的问题,请参考以下文章

在 Python 中对稀疏矩阵执行分解

用于文档分类的 scipy/sklearn 稀疏矩阵分解

奇异分解(SVD) 案例--用户与商家稀疏矩阵

避免使用 Eigen 分解稀疏矩阵时的动态内存分配

推荐系统中矩阵分解算法-funkSVD和ALS

推荐系统笔记:无任何限制的矩阵分解