我想了解句子的fastText向量的创建方式。根据{{3}},通过对单词向量进行平均来获得句子向量。
为了确认这一点,我编写了以下脚本:
import numpy as np
import fastText as ft
# Loading model for Finnish.
model = ft.load_model('cc.fi.300.bin')
# Getting word vectors for 'one' and 'two'.
one = model.get_word_vector('yksi')
two = model.get_word_vector('kaksi')
# Getting the sentence vector for the sentence "one two" in Finnish.
one_two = model.get_sentence_vector('yksi kaksi')
one_two_avg = (one + two) / 2
# Checking if the two approaches yield the same result.
is_equal = np.array_equal(one_two, one_two_avg)
# Printing the result.
print(is_equal)
# Result: FALSE
但是,似乎所获得的向量并不相似。
为什么两个值都不相同?它与我对向量求平均的方式有关吗?或者,也许我缺少一些东西?
答案 0 :(得分:0)
您可能会遇到浮点数学运算的问题-例如如果在CPU上进行了一次添加而在GPU上进行了一次添加,则可能会有所不同。
检查其是否正在执行所需操作的最佳方法是确保向量几乎完全相同。
您可能需要打印出两个向量并手动检查它们,或者对它自己做one_two减去one_two_avg的点积(即,两者之差的长度)。
答案 1 :(得分:0)
首先,您错过了
def l2_norm(x):
return np.sqrt(np.sum(x**2))
def div_norm(x):
norm_value = l2_norm(x)
if norm_value > 0:
return x * ( 1.0 / norm_value)
else:
return x
# Getting word vectors for 'one' and 'two'.
one = model.get_word_vector('yksi')
two = model.get_word_vector('kaksi')
eos = model.get_word_vector('\n')
# Getting the sentence vector for the sentence "one two" in Finnish.
one_two = model.get_sentence_vector('yksi kaksi')
one_two_avg = (div_norm(one) + div_norm(two) + div_norm(eos)) / 3
不仅仅是一个简单的“平均值”的部分。在FastText对每个单词向量求和之前,将每个向量除以其范数(L2范数),然后平均过程仅涉及具有正L2范数值的向量。
第二,句子始终以EOS结尾。因此,如果您尝试手动计算,则需要在计算平均值之前输入EOS。
尝试一下(我假设每个单词的L2范数都是正数):
p3 = print(p2.geturl())
urllib.request.urlretrieve(p3)