优化Gensim字符移动器的速度距离函数(wmdistance)

时间:2017-08-30 12:38:56

标签: python nlp nltk gensim word2vec

我使用gensim wmdistance来计算参考句和其他1000个句子之间的相似度。

    model = gensim.models.KeyedVectors.load_word2vec_format(
     'GoogleNews-vectors-negative300.bin', binary=True)
    model.init_sims(replace=True)  

    reference_sentence = "it is a reference sentence"
    other_sentences = [1000 sentences]
    index = 0
    for sentence in other_sentences: 
      distance [index] = model.wmdistance(refrence_sentence, other_sentences)
      index = index + 1

根据gensim source codemodel.wmdistance会返回以下内容:

emd(d1, d2, distance_matrix)

其中

d1 =  # Compute nBOW representation of reference_setence.
d2 =  # Compute nBOW representation of other_sentence (one by one).
distance_matrix = see the source code as its a bit too much to paste it here.

对于我的用例,此代码在两个方面效率低下。

1)对于参考语句,它重复计算距离函数emd(d1, d2, distance_matrix)的d1(1000次)。

2)这个距离函数由来自不同点的多个用户调用,对于相同的other_sentence重复model.wmdistance(doc1, doc2)的整个过程,并且计算成本很高。对于这1000次比较,大约需要7-8秒。

因此,我想将这两项任务分开。距离的最终计算:emd(d1, d2, distance_matrix)和这些输入的准备:d1,d2和距离矩阵。由于距离矩阵取决于两者,因此至少其输入准备应与最终矩阵计算隔离。

我的初步计划是创建三个自定义函数:

d1 = prepared1(reference_sentence)
d2 = prepared2(other_sentence)
distance_matrix inputs = prepare inputs 

是否可以使用此gensim功能执行此操作,还是应该使用自己的自定义版本?有什么想法和解决方案可以更好地解决这个问题吗?

1 个答案:

答案 0 :(得分:2)

你是正确的观察到这个代码可以重构&优化以避免重复操作,尤其是在针对更大的文档集评估一个引用/查询doc的常见情况下。 (任何此类改进也将是对gensim的一个受欢迎的贡献。)

简单地在计算之外准备单个文档可能不会带来很大的节省;在每种情况下,必须计算两个文档之间的所有单词到单词的距离。预先计算更大的distance_matrix(在相关词汇和系统内存允许的范围内)可能是有意义的,其中包括许多成对WMD计算所需的所有单词。

(尽管可能会预测所有的单词到单词的距离,使用像GoogleNews向量集这样的300万字的词汇,而仅仅是4字节的浮点距离,将它们全部存储起来很诱人至少需要18TB。因此,在可管理的批次文件上计算相关单词的距离可能更有意义。)

一种可能的启动方式是创建一个wmdistance()的变体,它明确地对一个文档而不是一组文档起作用,因此可以组合直方图/距离矩阵的创建,用于许多比较。一旦。

对于不需要所有 WMD值但只想要前N个最近结果的常见情况,在原始WMD文件中描述了一个优化,其中另一个更快的计算(称为'RWMD') )当文件不可能出现在前N个结果中时,可以用来推断,因此完全跳过那些文档的完整WMD计算。