K-means算法

目   录

一.概 念

二.聚 类 与 分 类 比 较

三.算 法 核 心 步 骤

四.相 关 实 例

五.K 值 的 选 择 方 法

六.优 缺 点

七.代码与结果展示

正   文

        一.概念

         K-means算法是硬聚类算法聚类是一种无监督学习,他将相似的对象归于一个簇中,簇中心通过簇中所有点的均值来计算,是典型的基于原型的目标函数聚类方法的代表,它是数据点到原型的某种距离作为优化的目标函数,利用函数求极值的方法得到迭代运算的调整规则。K-means算法以欧式距离作为相似度测度,它是求对应某一初始聚类中心向量V最优分类,使得评价指标J最小。算法采用误差平方和准则函数作为聚类准则函数,聚类算法与分类算法的主要区别就是分类的目标类别已知,而聚类的目标类别未知。

        二. 聚类与分类的比较

        聚类与分类:

 

 

  1. 在分类的过程中,测试样本点用×表示,数据带有标签(左下角红橙黑三色区分),经过分类后测试点×被分到了红色区域.
  2. 在聚类的过程中,图中左上角的原始数据分布散点图呈灰色,没有用特定的颜色(红色或橙色)区分,也就是说数据没有标签。聚类后将数据分为不同的簇,用红橙黑三色标记,见右上图。在一个簇中的数据就认为是同一类,也就是说这些数据具有相似性。

        三. 算法核心步骤    

 假设要把样本集分为c个类别,算法描述如下:

1)随机选取c个类的初始中心;

2)在第k次迭代中,对任意一个样本,求其到c个中心的距离,将该样本归到距离最短的中心所在的类;

3)类别划分完成后,重新确定类别的中心点,将类别中所有样本各特征的均值作为新的中心点对应特征的取值,即该类中所有样本的质心,利用均值等方法更新该类的中心值;

4)对于所有的c个聚类中心,如果利用2)和3)的迭代法更新后,值保持不变,则迭代结束,否则继续迭代。

完整步骤演示:

        四. 想关实例展示

          五. K值的选择方法

1.手肘法

手肘法的核心指标是SSE(sum of the squared errors,误差平方和),

其中,Ci是第i个簇,p是Ci中的样本点,mi是Ci的质心(Ci中所有样本的均值),SSE是所有样本的聚类误差,代表了聚类效果的好坏。

       手肘法的核心思想是:随着聚类数k的增大,样本划分会更加精细,每个簇的聚合程度会逐渐提高,那么误差平方和SSE自然会逐渐变小。并且,当k小于真实聚类数时,由于k的增大会大幅增加每个簇的聚合程度,故SSE的下降幅度会很大,而当k到达真实聚类数时,再增加k所得到的聚合程度回报会迅速变小,所以SSE的下降幅度会骤减,然后随着k值的继续增大而趋于平缓,也就是说SSE和k的关系图是一个手肘的形状,而这个肘部对应的k值就是数据的真实聚类数。当然,这也是该方法被称为手肘法的原因。

步骤:

1.计算k从1到n的的SSE
2.SSE会逐渐减小,直到k=n时SSE=0,每个点都是质心
3.在SSE减小过程,会出现拐点,这个拐点就是肘,下降率突然变缓时,就是最佳K值。

2. 轮廓系数法

该方法的核心指标是轮廓系数(Silhouette Coefficient),某个样本点Xi的轮廓系数定义如下:

  

 

其中,a是Xi与同簇的其他样本的平均距离,称为凝聚度,b是Xi与最近簇中所有样本的平均距离,称为分离度。而最近簇的定义是

其中p是某个簇Ck中的样本。事实上,简单点讲,就是用Xi到某个簇所有样本平均距离作为衡量该点到该簇的距离后,选择离Xi最近的一个簇作为最近簇。

       求出所有样本的轮廓系数后再求平均值就得到了平均轮廓系数。平均轮廓系数的取值范围为[-1,1],且簇内样本的距离越近,簇间样本距离越远,平均轮廓系数越大,聚类效果越好。那么,很自然地,平均轮廓系数最大的k便是最佳聚类数。

        六. 优缺点

 K-Means优点:
1)原理比较简单,实现也是很容易,收敛速度快。

2)聚类效果较优。

3)算法的可解释度比较强。

4)主要需要调参的参数仅仅是簇数k。

K-Means缺点:
1)K值的选取不好把握(改进:可以通过在一开始给定一个适合的数值给k,通过一次K-means算法得到一次聚类中心。对于得到的聚类中心,根据得到的k个聚类的距离情况,合并距离最近的类,因此聚类中心数减小,当将其用于下次聚类时,相应的聚类数目也减小了,最终得到合适数目的聚类数。可以通过一个评判值E来确定聚类数得到一个合适的位置停下来,而不继续合并聚类中心。重复上述循环,直至评判函数收敛为止,最终得到较优聚类数的聚类结果)。

2)对于不是凸的数据集比较难收敛(改进:基于密度的聚类算法更加适合,比如DESCAN算法)

3)如果各隐含类别的数据不平衡,比如各隐含类别的数据量严重失衡,或者各隐含类别的方差不同,则聚类效果不佳。

4) 采用迭代方法,得到的结果只是局部最优。

5) 对噪音和异常点比较的敏感(改进1:离群点检测的LOF算法,通过去除离群点后再聚类,可以减少离群点和孤立点对于聚类效果的影响;改进2:改成求点的中位数,这种聚类方式即K-Mediods聚类(K中值))。

 6)初始聚类中心的选择
        七. 代码与结果展示

代码展示

import numpy as np
import matplotlib.pyplot as plt

# 两点欧氏距离
def distance(e1, e2):
    return np.sqrt((e1[0]-e2[0])**2+(e1[1]-e2[1])**2)

# 集合中心
def means(arr):
    return np.array([np.mean([e[0] for e in arr]), np.mean([e[1] for e in arr])])#mean用于求取均值   arr存放某一个簇中的点
if __name__=="__main__":
    ## 生成二维随机坐标(如果有数据集就更好)
    arr = np.random.randint(0,100, size=(100, 2))

    ## 初始化聚类中心和聚类容器
    m = 5   #聚类个数
    k_arr=np.random.randint(0,100, size=(5, 2))#随机初始5个中心
    cla_temp = [[],[],[],[],[]] #存放每个簇中的点
  

    ## 迭代聚类
    n = 20  #迭代次数

    for i in range(n):    # 迭代n次
        for e in arr:    # 把集合里每一个元素聚到最近的类
            ki = 0        # 假定距离第一个中心最近
            min_d = distance(e, k_arr[ki])
            for j in range(1, k_arr.__len__()):
                if distance(e, k_arr[j]) < min_d:    # 找到更近的聚类中心
                    min_d = distance(e, k_arr[j])
                    ki = j
            cla_temp[ki].append(e)
        # 迭代更新聚类中心
        for k in range(k_arr.__len__()):
            if n - 1 == i:
                break
            k_arr[k] = means(cla_temp[k])
            cla_temp[k] = []

    ## 可视化展示
    col = ['HotPink', 'Aqua', 'Chartreuse', 'yellow', 'LightSalmon']    #仅提供了5种颜色
    for i in range(m):
        plt.scatter(k_arr[i][0], k_arr[i][1], linewidth=10, color=col[i])   #画中心的散点图
        plt.scatter([e[0] for e in cla_temp[i]], [e[1] for e in cla_temp[i]], color=col[i])  #画簇中的点
    plt.show()

结果展示:

 

  • 2
    点赞
  • 7
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值