【问题标题】:MATLAB nnmf() - large term-document matrix - memory and speed issueMATLAB nnmf() - 大型术语文档矩阵 - 内存和速度问题
【发布时间】:2012-08-21 13:55:34
【问题描述】:

我有一个很大的术语文档矩阵,想使用 matlab 提供的非负矩阵分解函数。问题是在第 1 次迭代之后,内存使用率迅速上升并达到顶峰(我的系统有 6GB),另一方面,CPU 使用率水平变得非常低(大约 1%-5%)。整个系统的行为就像它已经崩溃一样,只有等待很长时间才能完成第二次迭代。 (请注意,要获得好的结果需要更多的迭代)。

问题:

如果有人对此有任何经验,或者使用比我更大的矩阵运行 nnmf(),我真的很想知道他/她实际上是如何克服上述问题的。

另外:我使用较小的矩阵(约 7000x1800)完成了此操作,没有任何问题。我使用稀疏矩阵是因为术语文档矩阵有很多零元素,这有助于减少需要存储的空间。例如在我的例子中,Term-Document 矩阵有14608 * 18828 = 275039424 元素和sum(sum(spa~=0)) = 1312582 非零元素:

>> whos
Name          Size                    Bytes  Class     Attributes

full      14608x18828            2200315392  double              
spa       14608x18828              21151944  double    sparse    

【问题讨论】:

  • 我建议将变量命名为“full”是一个非常糟糕的主意,尤其是当您使用稀疏矩阵时,因为有一个名为 full.m 的函数。你在这里自找麻烦。
  • 你说得对,我没有使用完整的矩阵。我只是将其作为信息提供给您,以向您展示我的矩阵具有的稀疏性。

标签: matlab sparse-matrix term-document-matrix nmf


【解决方案1】:

我想我们都看过太多《星际迷航》剧集了。我们的计算机不是无限快的,也不是无限量的内存。我们期望我们几乎可以进行任何我们想要的计算,并且几乎立即获得结果,这让我们感到厌烦。仅仅因为您想要处理大型矩阵的分解并不意味着您将能够这样做。获得更多内存来处理这种大小的问题。或者解决较小的问题。

您描述的矩阵甚至不是非常稀疏,它们的分解将基本上是完全完整的。稀疏矩阵很少有价值,除非非零值的数量占总数的一小部分。只有 50% 零值的稀疏矩阵是对工具的浪费。例如,

>> A = randi([0 1],100, 100);
>> B = sparse(A);
>> whos
  Name        Size             Bytes  Class     Attributes

  A         100x100            80000  double              
  B         100x100            81480  double    sparse    

看到这里 A 是 50% 的零,但稀疏形式实际上比完整版本需要更多的内存来存储!请记住,您不仅需要存储非零元素,还需要存储它们的位置。

好的,所以稀疏存储效率不高。但是,您肯定可以在运营效率方面获得收益吗?甚至不是这样。使用 Steve Eddins timeit 函数进行比较,我得到以下结果:

>> timeit(@() A*A)
ans =
   7.3604e-05

>> timeit(@() B*B)
ans =
    0.0014884

因此,稀疏乘法比完全乘法慢得多。

本质上,只有 50% 为零的稀疏矩阵正在浪费稀疏形式的功能。如果矩阵更加稀疏,结果会有所不同。

【讨论】:

  • 感谢您让我更清楚地了解稀疏矩阵。我的矩阵有 14608*18828 =275039424 个元素和 sum(sum(spa~=0)) =1312582 个非零元素,所以 1312582/275039424 =0.0048 我认为我使用稀疏矩阵做得很好。我现在正试图找出 nnmf() 函数内部发生了什么,如果这个矩阵有时会变满......
【解决方案2】:

终于奏效了:

我检查了nnmf.m 文件(Matlab 提供的算法实现)并试图理解代码。有一个名为“d”的变量执行以下操作:d = a - w*h; 并且是与“a”具有相同维度的完整矩阵(即大型术语文档矩阵):

Name             Size                    Bytes  Class      Attributes
a            14608x18828              21151944  double     sparse    
d            14608x18828            2200315392  double               
...
h                4x18828                602496  double               
h0               4x18828                602496  double               
...
w            14608x4                    467456  double               
w0           14608x4                    467456  double   

为了节省一些内存空间,我使用clear 在不需要时删除了这个矩阵。 nnmf.m 文件的一部分:

d = a - w*h;
dnorm = sqrt(sum(sum(d.^2))/nm);
dw = max(max(abs(w-w0) / (sqrteps+max(max(abs(w0))))));
dh = max(max(abs(h-h0) / (sqrteps+max(max(abs(h0))))));
delta = max(dw,dh);

被这个新的替换了:

d = a - w*h;
dnorm = sqrt(sum(sum(d.^2))/nm);
clear d;
dw = max(max(abs(w-w0) / (sqrteps+max(max(abs(w0))))));
dh = max(max(abs(h-h0) / (sqrteps+max(max(abs(h0))))));
delta = max(dw,dh);

clear d 被添加到那里是因为 d 在那之后再也没有使用过。对于正在使用的术语文档矩阵,这可以正常工作而不会导致内存问题。

【讨论】:

    猜你喜欢
    • 2018-05-04
    • 2014-03-22
    • 1970-01-01
    • 2017-09-12
    • 1970-01-01
    • 2011-03-15
    • 1970-01-01
    • 2013-08-09
    • 1970-01-01
    相关资源
    最近更新 更多