【问题标题】:sparse matrix multiplication only calculate upper triangle稀疏矩阵乘法只计算上三角
【发布时间】:2016-06-09 10:51:08
【问题描述】:

我正在做一些关于去重字符串的事情。 我的主要工作流程是:

df = pd.read_csv(some_path)
vect = TfidfVectorizer(min_df=1)
tfidf = vect.fit_transform(df.title.astype(unicode))

sml_matrix = (tfidf * tfidf.T)
sml_matrix = sml_matrix> similar_ratio

sml_matrix 就像:

       │CHEESE CHORES GEESE  GLOVES
───────┼───────────────────────────
CHEESE │    1   0.222  0.177  0.444     
CHORES │0.222       1  0.422  0.333
GEESE  │0.177   0.422      1  0.300
GLOVES │0.444   0.333  0.300      1

显然,计算sml_matrix的上三角就足够了。

但我不知道如何只用 scipy.sparse 矩阵计算上三角。(我只能想象 forloop,但似乎效率不高)

for 循环示例(只是伪代码):

A = tfidf
T = tfidf.T
side_length = len(A)

for i in range(side_length):
    for j in range(side_length):
        if j < i:
            # avoid calculate lower triangle and diagonal
            continue
        maxtrix[i,j] = A(i)* T(j)

here,我看到numpy 有np.apply_along_axis(d, 0, _) 只计算上三角形,但scipy.sparse 没有。

更新:

无论数据集多大,只计算上三角会消耗更少的cpu资源。我对矩阵计算不熟悉,好奇让我问这个问题(如何只计算稀疏矩阵中的上三角),不是用于解决内存错误。

【问题讨论】:

  • 您可能会遇到填写问题。 tfidf * tfidf.T 可能会非常密集 - 例如,如果您在 tfidf 中只有一个密集列(即所有文档中都存在一个特征),那么您的 sml_matrix 将是 100% 密集的,即使其余的您的特征的出现非常稀少。如果您假设tfidf * tfidf.T 是完全密集的,您甚至可以将它的上三角形放在内存中吗?

标签: python numpy matrix scipy scikit-learn


【解决方案1】:

也许你可以通过一些技巧赢得 2 个内存因子,但数据大小总是在增长......

因此,最好接受它并将 Dataframe 分成块。 你可以这样做:

df=pd.DataFrame(np.random.rand(12)) # as a mini exemple
maxsize=4
df['group']=df.index//maxsize
df.set_index('group',append=True,inplace=True)
df2=df.reorder_levels([1,0])

from itertools import combinations

print(df)
for i,j in (combinations(df2.index.levels[0],2)):
    print (df2.loc[[i,j]])
    #or do something else. 

那么 df 是:

                  0
    group          
0   0      0.388695
1   0      0.982780
2   0      0.632253
3   0      0.445638
4   1      0.346920
5   1      0.789327
6   1      0.311657
7   1      0.548581
8   2      0.688201
9   2      0.824547
10  2      0.980281
11  2      0.314968

块是:

                  0
group           
0     0    0.388695
      1    0.982780
      2    0.632253
      3    0.445638
1     4    0.346920
      5    0.789327
      6    0.311657
      7    0.548581
                  0
group           
0     0    0.388695
      1    0.982780
      2    0.632253
      3    0.445638
2     8    0.688201
      9    0.824547
      10   0.980281
      11   0.314968
                  0
group           
1     4    0.346920
      5    0.789327
      6    0.311657
      7    0.548581
2     8    0.688201
      9    0.824547
      10   0.980281
      11   0.314968

然后计算并收集每个块上的好东西。 您将进行两次计算,但不会再出现内存错误。

【讨论】:

  • 感谢您的回答。我知道收缩数据集可以避免内存错误,但是这个问题的目的是解决“如何只计算上三角”。
  • 对于 Numpy,我认为这不可能以一种有效的方式。您可以使用 Numba 或 Cython 来完成,但由于 dot 是 numpy 更优化的功能之一,您将需要做很多工作才能达到相同的速度。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2011-03-07
  • 1970-01-01
  • 2017-07-21
  • 1970-01-01
  • 2012-09-04
  • 1970-01-01
相关资源
最近更新 更多