如何比较三个预训练模型的余弦相似度?

How to compare cosine similarities across three pretrained models?

我有两个语料库——一个是所有女性领导人的演讲,另一个是男性领导人的演讲。我想检验一个假设,即一个语料库中两个词之间的余弦相似度与另一个语料库中相同两个词之间的余弦相似度显着不同。这样的 t 检验(或等效)是否合乎逻辑且可能?

此外,如果两个语料库的余弦相似度不同,我如何检查第三个语料库中相同两个词之间的余弦相似度是否与第一个或第二个语料库更相似?

当然有可能。给定一定数量的数据,它是否有意义更难回答。

请注意,在单独的训练课程中,给定的单词 A 不一定会在相同的坐标中结束,这是由于算法使用的固有随机性。在 完全相同的数据 上进行训练时也是如此。

只是一般来说,distances/directions换句话说BC等应该是当有足够的 data/training 和精心选择的参数时,总体用途相似。所以ABC等可能在不同的地方,distances/directions – 但相对关系仍然相似,就词的邻域而言,或者 (A-B) 方向仍然可以预测某些人类可感知的意义差异(如果应用)换句话说 C 等等

因此,您应该避免在来自不同训练运行或语料库的单词之间进行直接余弦相似度比较,但您可能会发现相似度差异的意义(A-B vs A' - B' ) 或前 N 个列表或相对排名。 (这也可能是如何与第 3 个语料库进行比较:某些成对相似性或前 N 列表或相关词在其他词的 'most similar' 结果中的序数排名中存在多大程度的差异或相关性。 )

您可能想对您的措施进行完整性检查,查看它们在逻辑上 "shouldn't" 的比较中暗示有意义差异的程度。例如,针对完全相同的语料库进行多次运行,只是蜜蜂重新洗牌,或者针对完全相同的语料库的随机子集。 (在检查 word2vec 模型之间差异的重要性时,我不知道有什么像 't-test' 这样正式的东西,但是检查一些差异是否足以区分真正不同的语料库和 1/N 随机子集相同的语料库,达到一定的置信度可能是断言有意义差异的基础方法。)

在某种程度上,"oughtta be very similar" 运行显示的最终向量结果明显不同,这可能暗示:

  • 语料库太小,每个单词的不同用法示例太少 - word2vec 受益于大量数据,与有时数百亿的训练相比,政治演讲集可能非常小用于大型 word2vec 模型的单词

  • 模型参数化错误 - 模型过大(因此容易过度拟合),或训练次数不足,或其他次优参数可能会产生对于相同训练数据变化更大的模型

您还需要注意训练语料库大小的不匹配。一个 10 倍大的语料库意味着更多的单词将通过固定的 min_count 阈值,并且任何选择的 N epochs 训练将涉及 10 倍的常见示例-words,并在更大(向量大小)的模型中支持稳定的结果——而具有较小语料库的相同模型参数会给出更不稳定的结果。

您可以考虑的另一种技术是将语料库组合成一个训练集,但根据相关说话人的不同,将感兴趣的关键词的标记修改为不同。例如,您可以将单词 'family' 替换为 'f-family''m-family',具体取决于说话者的性别。 (您可以对每次出现或部分出现都执行此操作。您也可以将每个演讲不止一次地输入到您的语料库中,有时使用实际单词,有时将部分或全部替换为上下文标记的替代词。 )

在那种情况下,您将得到一个最终模型,并且 words/context-tokens 在 'same' 坐标 space 中用于直接比较。但是,伪词 'f-family''m-family' 会更多地受到它们特定于上下文的用法的影响 - 因此它们的向量可能彼此不同,并且与原始的 'family' (如果你'我们还以有趣的暗示方式保留了未修改的使用实例)。

另请注意:如果使用原始 Google word2vec 代码版本的 'analogy-solving' 方法,或其他遵循其示例的库(如 gensim),请特别注意不会 return 作为输入提供的任何单词的答案。因此,在通过调用 model.most_similar(positive=['doctor', 'woman'], negative=['man']) 解决充满性别的类比 'man' : 'doctor' :: 'woman' : _?_ 时,即使基础模型 still 具有 'doctor' 作为最接近的词目标坐标,它会作为输入词之一自动跳过,而是产生第二个最接近的词。

一些早期的 "bias-in-word-vectors" 文章忽略了这个细节,因此往往暗示更大的偏差,由于这个实现工件,即使这样的偏差很小甚至不存在。 (您可以向 most_similar() 提供原始向量而不是字符串标记 - 然后获得完整结果,无需对输入标记进行任何过滤。)