机器学习实战第十章 K-均值聚类

本文介绍了K-均值聚类算法的基本原理和步骤,通过一个学生数据的例子展示了如何进行聚类。算法涉及随机选择初始质心,计算数据点与质心的距离并分配到最近的簇,然后更新质心。还提到了二分K-均值算法来解决局部最优问题。文章讨论了聚类效果的评估和后处理策略,并给出了实际的地理坐标聚类案例。

1.算法简例

K-均值是一种聚类算法,通过将数据点分配到离其最近的中心点所代表的群体,又称为,将数据集分成K个不重叠的簇,以实现数据的聚类分析和归类,接下来用一个简单的例子来说明

假设我们有以下五个学生的数据,每个学生有两个特征:年龄和成绩。

学生编号 年龄 成绩
1 20 80
2 23 85
3 25 75
4 30 60
5 28 70

现在的目标是使用K均值算法将这些学生分为两个簇,(K=2)

  1. 假设我们选择学生1和学生4作为初始群体中心(这俩年龄和分数差最大),也就是质点
  2. 然后我们分别计算每个学生与两个簇的距离,将每个学生分配到距离最近的簇所代表的群体中。对于学生1和学生4来说,它们是质心,所以它们自己就是属于自己的簇。对于其他学生,我们计算它们与两个簇的距离:
    • 对于学生2来说,距离质心1的距离是3,距离质心2的距离是10,所以学生2被分配到簇1
    • 对于学生3来说,距离质心1的距离是5,距离质心2的距离是5,所以学生3被分配到簇1
    • 对于学生5来说,距离质心1的距离是8,距离质心2的距离是2,所以学生5被分配到簇2

现在我们有以下两个簇:

群体学生 质心
簇1 {学生1, 学生2, 学生3} {学生1}
簇2 {学生4, 学生5} {学生4}
  1. 更新质心:
    对于每个簇,我们计算簇中所有学生的年龄和成绩的平均值,然后将这些平均值作为新的群体中心。
    簇1的新质心:年龄平均值 = (20+23+25)/3=22.67,成绩平均值 = (80+85+75)/3=80
    簇2的新质心:年龄平均值 = (30+28)/2=29,成绩平均值 = (60+70)/2=65
  2. 重复步骤2和步骤3:
    现在,我们重新计算每个学生与新的质心的距离,并将学生重新分配到最近的质心所代表的簇中。然后更新质心。迭代此过程直到质心不再发生变化或达到预定的迭代次数。在这个例子中,我们只进行一次迭代后,质心不再发生变化,所以算法停止。

最终,我们得到了两个群体:

群体学生 质心
簇1 {学生1, 学生2, 学生3} {学生1}
簇2 {学生4, 学生5} {学生4}

以上就是一个简单的K均值算法的例子,它将学生根据年龄和成绩特征分成了两个群体簇

2.算法原理

通过以上的例子,可以总结出K-均值的算法流程:先随机确定k个初始质心,再将数据集中所有点分配到一个簇中,根据每个点到最近质心的距离来进行簇的分类,之后重新计算每个簇的质心,重复以上过程直到质心不再变化

要注意的是,K-均值的分类性能与计算质心的距离有关,下面给出K-均值的各个支持函数

def loadDataSet(fileName):      # 通用函数用于解析制表符分隔的浮点数
    dataMat = []                # 假设最后一列是目标值
    fr = open(fileName)
    for line in fr.readlines():
        curLine = line.strip().split('\t')
        fltLine = list(map(float, curLine))  # 将所有元素映射为浮点数
        dataMat.append(fltLine)
    return dataMat

def distEclud(vecA, vecB):
    return sqrt(sum(power(vecA - vecB, 2)))  # 返回欧几里得距离 (la.norm(vecA-vecB))

def randCent(dataSet, k):
    n = shape(dataSet)[1]
    centroids = mat(zeros((k, n)))  # 创建centroid矩阵
    for j in range(n):  # 在每个维度的范围内创建随机的聚类中心
        minJ = min(dataSet[:, j])
        rangeJ = float(max(dataSet[:, j]) - minJ)
        centroids[:, j] = mat(minJ + rangeJ * random.rand(k, 1))
    return centroids

这些代码是K-均值算法的一部分,包含了加载数据集、计算欧几里得距离以及生成随机聚类中心的功能。其中loadDataSet函数用于从文件中加载数据集,distEclud函数用于计算两个向量之间的欧几里得距离,randCent函数用于生成K个随机的聚类中心,作为算法的初始中心点。这些函数在K-均值算法的实现中都是非常重要的组成部分
请添加图片描述
切片查看矩阵的相关数值如上,通过randCent也能生成最小最大值之间的数值,distEclud也能计算距离,所有的函数都正常,下面就是K-均值的核心代码部分

def kMeans(dataSet, k, distMeas=distEclud, createCent=randCent):
    m = shape(dataSet)[0]
    clusterAssment = mat(zeros((m, 2)))  # 创建矩阵以分配数据点到聚类中心,并保存每个点的误差平方和
    centroids = createCent(dataSet, k)  # 使用给定函数(默认为randCent)生成初始的聚类中心
    clusterChanged = True
    while clusterChanged:
        clusterChanged = False
        for i in range(m):  
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值