我正在尝试用Java编写一组关于特定主题的新闻文章。我使用Crawler4J抓取了有关特定主题的新闻网站,将我自己的TF / IDF实现与语料库进行比较(有理由说我没有使用内置的Weka或TF / IDF的其他实现,但它们可能已经出来了这个问题的范围)并应用了一些其他特定于域的逻辑,这些逻辑为每个文档留下了一袋单词+权重(我将其存储在值为0到1之间的Map中)。我想通过查看单词权重来聚类关于类似主题的文章,所以我开始使用Weka的EM和SimpleKMeans群集。问题是我得到了相当不起眼的结果,我正在试图弄清楚我是否可以采取任何措施来更好地调整聚类。
例如,在约300篇文章的玩具数据集中,如果我将每个文档中的单词修剪为前20,然后使用全套单词作为特征,我最终得到~2k独特的功能。我正在使用每篇文章作为训练实例,并尝试使用一些不同的参数来调整SimpleKMeans聚类器(例如~20-30个聚类,100个最大迭代)。当我一眼就看到数据时,我发现很多文章的关键词看起来非常密切相关,所以我期望高质量的结果和一堆包含~5-10篇文章的集群。不幸的是,结果通常是一个具有>的群集。一半的文章,一堆有1篇文章的群集,还有一些有2-5篇文章的散兵游客。
这些结果是预期的,还是有办法获得更高质量的结果?请注意,我还研究了LingPipe和其他提供集群功能的框架,并使用滚动我自己的EM实现(具有适度但不是很大的成功)。在此先感谢您的帮助!
答案 0 :(得分:6)
有几个技巧可以让 k -means为文本工作:
为什么规范化起作用的简短解释:假设你有三个文件{d 1,d 2,d 3}和微小的词汇{cat,dog,tax}。术语 - 文档矩阵(原始计数或tf-idf,无关紧要)看起来像
| cat | dog | tax
d₁ | 100 | 100 | 0
d₂ | 10 | 10 | 0
d₃ | 0 | 0 | 100
现在我们要做2-means。我们可以合理地期望找到一个宠物群{d 1,d 2}和一个融资单群{d 3}。但是,对之间的距离是
D(d₁, d₂) = 127.28
D(d₁, d₃) = 173.21
D(d₂, d₃) = 101.00
因此,像 k -means这样的基于密度的方法倾向于将d 2与d 3分组。通过对矢量进行归一化,可以有效地将d 1和d 2映射到相同的矢量[0.71,0.71,0],因此D(d 1,d 2)= 0,它们将始终位于同一个簇中。
( k - 应用于规范化向量的方法有时被称为“球形” k - 意思,因为单位向量位于以原点为中心的超球面上。)
答案 1 :(得分:2)
如果你有一些单词和它们的权重,那么你应该首先计算它们之间的一些相似性度量。例如Jacquard Similarity,Cosine Similarity ....然后使用此基础,您可以使用K-Means或其他聚类算法对文章进行聚类。
如果您知道新闻文章只能是固定类型,如体育,娱乐,历史,政治等,那么我建议您使用分类算法而不是聚类算法,这将增加您获得良好和令人印象深刻的结果的概率。
如果真的想使用聚类算法,可以使用一些可以生成动态聚类的扩展算法(最近邻,遗传算法,质量阈值,最小生成树......)。
答案 2 :(得分:1)
k均值和EM模型通过它们的均值向量聚类,并且相似性基于欧几里德和。 Mahalanobis距离。
问题是平均值可能对稀疏数据不敏感。这可以通过手段比文档稀疏这一事实得到最好的结果。此外,甚至可能发生手段变得彼此更相似而不是实际文件。
所以恕我直言,你只是在为你的数据使用不合适的聚类算法。有时它可能工作正常,但有时它会失败,因为该方法是针对每个轴中具有相同方差的密集数据而设计的。