如何正确使用 scikit-learn 进行文本聚类

Posted

技术标签:

【中文标题】如何正确使用 scikit-learn 进行文本聚类【英文标题】:How to use scikit-learn properly for text clustering 【发布时间】:2017-03-22 20:02:34 【问题描述】:

使用 TfidfVectorizer 进行 kmeans 聚类时总是出错。

有3种情况:

    我在 TfidfVectorizer 中使用 tokenizer 参数为我的数据集自定义标记化过程。这是我的代码:

`

vectorizer = TfidfVectorizer(stop_words=stops,tokenizer=tokenize)
X = vectorizer.fit_transform(titles)

`

但是我得到了这个错误:

ValueError: empty vocabulary; perhaps the documents only contain stop words
    我为作为标记化结果的每个术语创建了一个包含术语和文档频率的词汇表,因此代码如下所示:

vectorizer = TfidfVectorizer(stop_words=stops,tokenizer=tokenize,vocabulary=vocab)

但我又遇到了一个新错误:

ValueError: Vocabulary contains repeated indices.

最后,我删除了分词器和词汇参数。代码变成这样:

`

vectorizer = TfidfVectorizer(stop_words=stops)
X = vectorizer.fit_transform(titles)
terms = vectorizer.get_feature_names()
true_k = 8
model = KMeans(n_clusters=true_k, init='k-means++', max_iter=100, n_init=1)
model.fit(X)
print "Top terms per cluster:"
order_centroids = model.cluster_centers_.argsort()[:, ::-1]
for i in range(true_k):
    print "Cluster %d:" % i,
    for ind in order_centroids[i, :10]:
        print ' %s' % terms[ind],
    print

`

嗯,程序运行成功但是聚类结果是这样的:

`

Cluster 0:  bangun,  rancang,  lunak,  perangkat,  aplikasi,  berbasis,  menggunakan,  service,  sistem,  pembangunan,
Cluster 1:  sistem,  aplikasi,  berbasis,  web,  menggunakan,  pembuatan,  mobile,  informasi,  teknologi,  pengembangan,
Cluster 2:  android,  berbasis,  aplikasi,  perangkat,  rancang,  bangun,  bergerak,  mobile,  sosial,  menggunakan,
Cluster 3:  implementasi,  algoritma,  menggunakan,  klasifikasi,  data,  game,  fuzzy,  vector,  support,  machine,
Cluster 4:  metode,  menggunakan,  video,  penerapan,  implementasi,  steganografi,  pengenalan,  berbasis,  file,  analisis,
Cluster 5:  citra,  segmentasi,  menggunakan,  implementasi,  metode,  warna,  tekstur,  kembali,  berwarna,  temu,
Cluster 6:  jaringan,  tiruan,  protokol,  voip,  syaraf,  saraf,  menggunakan,  implementasi,  kinerja,  streaming,
Cluster 7:  studi,  kasus,  its,  informatika,  teknik,  sistem,  informasi,  data,  surabaya,  jurusan,

`

有些词条被聚集成多个簇,比如词条data被放置到簇3和簇7中。

您能告诉我如何正确使用 tfidfvectorizer 和 KMeans 吗?你的帮助就是我的幸福:)

【问题讨论】:

什么是titles, 'vocab' ? Can you tell me how to use the tfidfvectorizer and KMeans properly? 作为一个问题太模糊了。你可以写很多关于它的内容。 您的结果没有问题。一个词可以以不同的概率出现在不同的集群中。 【参考方案1】:

如果你想知道你可以拥有的每个术语的集群:

vectorizer = TfidfVectorizer(stop_words=stops)
X = vectorizer.fit_transform(titles)
terms = vectorizer.get_feature_names()
true_k = 8
model = KMeans(n_clusters=true_k, init='k-means++', max_iter=100, n_init=1)
model.fit(X)

terms_vectorized = vectorizer.transform(terms)
terms_prediction = model.predict(terms_vectorized)

然后,您将获得可以迭代的每个术语的预测。

您的结果显示了每个聚类中术语的重要性,而不是它们的预测。

你得到这些错误的原因是因为你不能有一个没有术语的输入文档,并且不知何故你传递给矢量化器的参数导致一些文档是这样的。

【讨论】:

当我将参数标记器用于我自己的标记函数时,你能告诉我为什么矢量化器会传递空词汇吗?上面集群中的术语根本没有被阻止,所以我不得不使用一个函数来阻止它们。非常感谢:) 即使对于您的一个文档,您的矢量化器没有找到一个术语,它也会抛出该错误。您可以单独对所有文档运行标记器,以找出哪个文档没有任何术语(不包括停止术语)。如果你找到那个文件,你就会知道问题所在。您还可以通过在所有文档中添加一个虚拟术语来解决问题,这样它们都不是空的(例如,在所有文档中添加“虚拟”一词)。

以上是关于如何正确使用 scikit-learn 进行文本聚类的主要内容,如果未能解决你的问题,请参考以下文章

使用 scikit-learn 进行聚类

文本聚类和主题提取

如何从 scikit-learn KMeans 中获取聚类中心的文本?

如何在 scikit-learn 中使用 KDE(核密度估计)进行一维数组聚类?

scikit-learn kmeans 用 Ja​​ccard 距离聚类文本

学习笔记Scikit-learn文本聚类实例