sklearn+python:无监督学习之k_means

版权声明:本文为博主原创文章,转载请标明原始博文地址。 https://blog.csdn.net/yuanlulu/article/details/81053726

K均值简介

K均值是一种无监督学习算法,在没有标签的训练样本中学习到聚类的中心点,后续测试数据可以计算和聚类中心的距离,归类到距离最近的聚类中心上。

随机初始化

只要K的值比样本少,可以随机选择K个样本作为初始簇心。初始化状态的不同,最终得到的结果也会不同,有些情况下K均值会收敛到局部最优解。

解决局部最优的方法就是多次随机初始化运行,选择最终成本最小的分类方案。

但是如果K特别大,要运行很多次才能明显改善。所以这种办法主要用在聚类数较少的情况下。

K值选择

聚类的数量是一个超参,一般根据图像化的结果或者经验来指定。

有两种有有用的原则可参考:

  • 肘部法则(学习曲线):不断增加K的值,把畸变(失真值)画出来,在拐弯的地方可以选为聚类的数量。
    但是实际情况可能没有那么明显的拐角,所以这个方法不是很好用。

  • 根据下游需求:有时也可以根据下游的需求来考量多少K是合适的。比如T恤的尺码分类,具体几个尺码要考虑后续商业上是否赚钱。

sklearn中使用k均值

生成200个数据,然后使用前180个训练,后20个测试:

from sklearn.datasets import make_blobs
from sklearn.cluster import KMeans

X, y = make_blobs(n_samples=200, n_features=2, centers=3, cluster_std=1,
                  center_box=(-10.0, 10.0), shuffle=True, random_state=1)

n_clusters = 3

kmean = KMeans(n_clusters=n_clusters, init='k-means++', random_state=1)
#kmean = KMeans(n_clusters=n_clusters, init='random', random_state=1)
kmean.fit(X[:180])
pre = kmean.predict(X[180:])
print('lable:{}, \npredict:{}'.format(y[180:], pre))

print('kmean, k={}, cost={}'.format(n_clusters, int(kmean.score(X))))

输出内容为:

lable:[1 2 0 1 1 2 2 2 1 0 1 1 0 2 1 1 0 0 1 0], 
predict:[0 2 1 0 0 2 2 2 0 1 0 0 1 2 0 0 1 1 0 1]
kmean, k=3, cost=-375

可以看到,生成的标签和测试预测的标签不太一致,那是因为生成数据的标签ID和聚类的标签ID不一样,仔细对比发现预测的和生成的标签还是很准的。

其中KMeans.score()计算拟合后的成本,用负数表示,绝对值越大说明成本越高。它计算的是训练样本到所属聚类中心点的距离的总和。

另外,在make_blobs的时候,传入一个random_state对应一个固定的score,换一个random_state,又变为另一个score,严重怀疑svklearn实现的KMeans初始化是否真的随机的。

猜你喜欢

转载自blog.csdn.net/yuanlulu/article/details/81053726