【问题标题】:scikit kmeans not accurate cost \ inertiascikit kmeans 不准确的成本\惯性
【发布时间】:2016-04-17 18:32:43
【问题描述】:

我想获得 k-means 成本(inertia 在 scikit kmeans 中)。 提醒一下:

成本是每个点到最近集群的距离平方和。

我在 scikit('inertia') 的成本计算之间发现了一个奇怪的差异,
以及我自己计算成本的简单方法

请看下面的例子:

p = np.random.rand(1000000,2)
from sklearn.cluster import KMeans
a = KMeans(n_clusters=3).fit(p)
print a.inertia_ , "****"

means = a.cluster_centers_
s = 0
for x in p:
    best = float("inf")
    for y in means:
        if np.linalg.norm(x-y)**2 < best:
            best = np.linalg.norm(x-y)**2
    s += best
print s, "*****"

我运行的输出是:

66178.4232156 ****
66173.7928716 *****

在我自己的数据集上,结果更显着(20% 的差异)。
这是 scikit 实现中的错误吗?

【问题讨论】:

    标签: python numpy machine-learning scikit-learn k-means


    【解决方案1】:

    首先 - 它似乎不是一个错误(但肯定是丑陋的不一致)。这是为什么?您需要仔细查看代码实际在做什么。为此,它从_k_means.pyx调用cython代码

    (第 577-578 行)

        inertia = _k_means._assign_labels_array(
            X, x_squared_norms, centers, labels, distances=distances)
    

    它的作用本质上就是您的代码,但是...在 C 中使用 doubles。所以也许这只是一个数字问题?让我们测试您的代码,但现在,具有清晰的集群结构(因此没有可能分配给许多中心的点 - 取决于数值准确性)。

    import numpy as np
    from sklearn.metrics import euclidean_distances
    
    p = np.random.rand(1000000,2)
    p[:p.shape[0]/2, :] += 100 #I move half of points far away
    
    from sklearn.cluster import KMeans
    a = KMeans(n_clusters=2).fit(p) #changed to two clusters
    print a.inertia_ , "****"
    
    means = a.cluster_centers_
    s = 0
    for x in p:
        best = float("inf")
        for y in means:
            d = (x-y).T.dot(x-y)
            if d < best:
                best = d
        s += best
    print s, "*****"
    

    结果

    166805.190832 ****
    166805.190946 *****
    

    有道理。因此,问题在于存在“靠近边界”的样本,这些样本可能会根据算术精度分配给多个集群。不幸的是,我无法准确追踪差异的来源。

    有趣的事情是实际上有一个不一致来自这个事实,inertia_ 字段充满了 Cython 代码, .score 调用 NumPy 之一。因此,如果您调用

    print -a.score(p)
    

    你会得到完全你的惯性

    【讨论】:

    • 是的,但是当在其他一些差异为 20% 的数据集上测试它时,这个问题变得很重要。你怎么看?
    • 我在他们的 github 上发布了这个问题,因为这肯定需要仔细查找。我建议你现在使用-a.score(X),因为它至少与你的其余代码一致(我假设它是用python编写的)。
    • 请给我一个链接
    • 似乎使用 sklearn 0.17 问题消失了github.com/scikit-learn/scikit-learn/issues/…
    猜你喜欢
    • 2021-04-17
    • 2018-08-14
    • 1970-01-01
    • 2014-05-11
    • 2015-02-20
    • 1970-01-01
    • 2013-10-24
    • 2019-06-07
    • 2015-07-31
    相关资源
    最近更新 更多