我试着根据句子之间的相似性把它们聚类。我使用ELMo生成句子的嵌入(其中它为每个单词生成嵌入,我将所有这些相加并除以单词数)。在
我最初尝试用tsne来拟合这些数据,通过ELMo生成的嵌入(512维),我能够形成簇,但是这里的问题是,在tsne中,维数必须减小,最多可以容纳3维。因此,输出不是那么准确。 然后我尝试使用DBSCAN,在这里我看不到任何与输入维度有关的约束(如果我错了,请纠正我)。在
现在我被用DBSCAN绘制的预测所震惊。另外,当我尝试打印预测的标签时,所有的标签都是'-1'。 有没有其他方法可以将句子聚类,或者如何有效地利用512维嵌入来用tsne或dbscan聚类句子?在
def tsnescatterplot(sentences):
arr = np.empty((0, 512), dtype='f')
word_labels = []
for sentence in sentences:
wrd_vector = get_elmo_embeddings(sentence)
print(sentence)
word_labels.append(sentence)
arr = np.append(arr, np.array([wrd_vector]), axis=0)
print('Printing array')
print(arr)
# find tsne coords for 2 dimensions
tsne = TSNE(n_components=2, random_state=0)
np.set_printoptions(suppress=True)
Y = tsne.fit_transform(arr)
x_coords = Y[:, 0]
y_coords = Y[:, 1]
# display scatter plot
plt.scatter(x_coords, y_coords)
for label, x, y in zip(word_labels, x_coords, y_coords):
plt.annotate(label, xy=(x, y), xytext=(0, 0), textcoords='offset points')
plt.xlim(x_coords.min() + 0.5, x_coords.max() + 0.5)
plt.ylim(y_coords.min() + 0.5, y_coords.max() + 0.5)
plt.show()
def dbscan_scatterplot(sentences):
arr = np.empty((0, 512), dtype='f')
for sentence in sentences:
wrd_vector = get_elmo_embeddings(sentence)
arr = np.append(arr, np.array([wrd_vector]), axis=0)
dbscan = DBSCAN()
np.set_printoptions(suppress=True)
Y = dbscan.fit(arr)
DBSCAN参数的选择具有重要意义。在
它提供默认值是愚蠢的,因为这些值只适用于低维的玩具数据。相反,它们应该要求用户指定值。在
你需要适当地选择特别是epsilon。但对于高维数据,很难选择这种井。您将发现结果突然从all-1(没有聚集)变为all-0(所有连接的内容),选择一个好的值很困难。在文献中有一些关于这一点的启发,你需要去探索。在
最后但并非最不重要的是,平均词向量往往会产生相当的坏结果。因为他们都朝着中庸的方向发展。越长的文档越接近平均值,越短的文档越远。但这并不是你想要的集群。。。这种额外的失真可能足以破坏你以前的信号。在
相关问题 更多 >
编程相关推荐