【发布时间】:2017-08-08 12:32:30
【问题描述】:
我正在尝试构建一种通用方法来计算许多稀疏向量(长度为 250k 的 100k 向量)的距离矩阵。在我的示例中,数据以 scipy csr 矩阵表示。这就是我正在做的:
首先,我定义了一种将 csr 行转换为 pyspark SparseVectors 的方法:
def csr_to_sparse_vector(row):
return SparseVector(row.shape[1], sorted(row.indices), row.data)
现在我将行转换为向量并将它们保存到一个列表中,然后将其提供给 SparkContext:
sparse_vectors = [csr_to_sparse_vector(row) for row in refs_sample]
rdd = sc.parallelize(sparse_vectors)
在下一步中,我使用笛卡尔函数来构建所有对(类似于这篇文章:Pyspark calculate custom distance between all vectors in a RDD)
在这个实验中,我想使用相应定义的 tje Jaccard Similarity:
def jacc_sim(pair):
dot_product = pair[0].dot(pair[1])
try:
sim = dot_product / (pair[0].numNonzeros() + pair[1].numNonzeros())
except ZeroDivisionError:
return 0.0
return sim
现在我应该只映射函数并收集结果:
distance_matrix = rdd2.map(lambda x: jacc_sim(x)).collect()
我在一个只有 100 个文档的小样本上运行此代码,一个本地机器和一个具有 180 个节点的集群。该任务需要很长时间并最终崩溃:https://pastebin.com/UwLUXvUZ
有什么建议可能是错的吗?
此外,如果距离度量是对称的 sim(x,y) == sim(y,x),我们只需要矩阵的上三角形。我发现一个帖子通过过滤解决了这个问题(Upper triangle of cartesian in spark for symmetric operations: `x*(x+1)//2` instead of `x**2`):
rdd2 = rdd.cartesian(rdd).filter(lambda x: x[0] < x[1])
但这不适用于 SparseVectors 列表。
【问题讨论】:
标签: python apache-spark scipy pyspark sparse-matrix