十五、机器学习进阶知识:K-Means聚类算法

文章目录

  • 1、聚类概述
  • 2、K-Means聚类算法原理
  • 3、K-Means聚类实现
    • 3.1 基于SKlearn实现K-Means聚类
    • 3.2 自编写方式实现K-Means聚类
  • 4、算法不足与解决思路
    • 4.1 存在的问题
    • 4.2 常见K值确定方法
    • 4.3 算法评估优化思路

1、聚类概述

聚类(Clustering)是指将不同的对象划分成由多个对象组成的多个类的过程,由聚类产生的数据分组,同一组内的对象具有相似性,不同组的对象具有相异性,它是一类机器学习基础算法的总称,聚类的核心计算过程是将数据对象集合按相似程度划分成多个类,划分得到的每个类称聚类的簇。
簇(Cluster)是由距离邻近的对象组合而成的集合。聚类的最终目标是获得紧凑、独立的簇集合。一般采用相似度作为聚类的依据,两个对象的距离越近,其相似度就越大。
由于聚类时待划分的类别未知,即训练数据没有标签,因此聚类的准确率相对于分类而言较低一点,但是聚类最大的特点是可以发现新知识、新规律,因此,聚类也是了解未知世界的一种重要手段。聚类可以单独实现,通过划分寻找数据内在分布规律,也可以作其他学习任务的前驱过程。
由于聚类使用的数据是无标记的,因此聚类属于非监督学习。聚类本质上仍然是对数据类别进行划分的问题,但是由于没有固定的类别标准,因此聚类的核心问题是如何定义簇。最常用的方法是依据样本间距离、样本的空间分布密度等来确定。按照簇的定义和聚类的方式,聚类大致分为以下几种:K-Means 为代表的簇中心聚类、基于连通性的层次聚类、以EM算法为代表的概率分布聚类、以 DBSCAN 为代表的基于网格密度的聚类,以及高斯混合聚类等。

2、K-Means聚类算法原理

K-Means 聚类算法也称为K均值聚类算法,是典型的聚类算法。对于给定的数据集和需要划分的类数k,算法根据距离函数进行迭代处理,动态地把数据划分成k个簇(即类别),直到收敛为止。簇中心也称为聚类中心。
K-Means 聚类的优点是算法简单、运算速度快,即便数据集很大计算起来也较便捷。不足之处是如果数据集较大,容易获得局部最优的分类结果,而且所产生的类的大小相近,对噪声数据也比较敏感。
K-Means 算法的实现过程较为简单,首先选取k个数据点作为初始的簇中心,即聚类中心。初始的聚类中心也被称作种子。然后,逐个计算各数据点到各个聚类中心的距离,把数据点分配到离它最近的簇。一次选代之后,所有的数据点都会分配给某个簇。再根据分配结果计算出新的聚类中心,并重新计算各数据点到各种子的距离,根据距离重新进行分配。不断重复计算和重新分配的步骤,直到分配不再发生变化或满足终止条件为止。
算法的整体流程如下:

随机选择k个点作为聚类中心
while 不满足终止条件:for 数据集中的每个数据点:for k个聚类中心:计算每个点到每个聚类中心的距离比较滞后将数据点分配到最近的聚类中心for 每个簇:对聚类中心进行更新,更新为簇内所有点的均值

在上述过程中,终止条件一般可以设置为循环次数或者较小的误差值等。

由于聚类对划分的类别没有固定的定义,因此也没有固定的评价指标,一般来说聚类算法的理想目标是类内距离最小,类间的距离最大,因此,通常依此目标建立K-Means 聚类的目标函数。
假设数据集X包含n个数据点,需要划分到k个类。聚类中心用集合U表示。聚类后所有数据点到各自聚类中心的差的平方和为聚类平方和,用J表示,则J值的计算过程如下:
在这里插入图片描述

聚类的目标就是使J值最小化,如果在多次迭代之后,J值不再发生变化,说明簇的分配不再发生变化,算法已经收敛。另外计算每个点到聚类中心的距离一般采用欧氏距离进行计算。

3、K-Means聚类实现

3.1 基于SKlearn实现K-Means聚类

SKlearn的cluster模块中提供的KMeans类可以帮助实现K-means聚类,其语法格式如下:

sklearn.cluster.KMeans(n_clusters=8,init='k-means++',n_init=10,max_iter=300,tol=0.0001,precompute_distances='auto',verbose=0,random_state=None,copy_x=True,n_jobs=None,algorithm='auto')

在上述格式中,n_clusters表示要形成的簇的数目,即类的数量,为可选项,默认为8;init用于接收待定的string,k-means++表示该初始化策略选择的初始均值向量之间都距离比较远,它的效果较好;n_init表示用不同种子运行K-Means 算法的次数,默认为10;max_iter表示单次运行的K-Means 算法的最大迭代次数,默认300;tol表示算法收敛的阈值;precompute_distances可选参数为Boolean或auto,表示是否提前计算好样本之间的距离;verbose表示是否输出日志信息,取值为0时表示不输出,取值越大,打印次数越频繁;random_state表示随机数生成器的种子;copy_x表示在进行距离计算前,是否要将数据居中以提高计算准确性,True表示不修改数据;n_jobs表示任务使用的CPU数量;algorithm表示对K-Means经典算法的选择。

返回KMeans 対象的属性主要有:
cluster_centers_:数组类型,各个簇中心的坐标。
labels_:每个数据点的标签。
inertia_:浮点型,数据样本到它们最接近的聚类中心的距腐平方和。
n_iter_:运行的选代改数。

KMeans类主要提供三个方法,功能及语法格式分别如下:
fit方法用于进行K-means聚类计算。

fit(X[,y,sample_weight])

predict方法用于预测X中的每个样本所属的最近簇。

predict(X[,sample_weight])

fit_predict用于计算簇中心,并预测每个样本的所属簇。

fit_predict(X[,y,sample_weight])

例:对sklearn中提供的鸢尾花数据集进行聚类。

from sklearn import datasets
from sklearn.cluster import KMeans
iris = datasets.load_iris()    #数据导入
X = iris.data    #将特征数据作为聚类数据
y = iris.target   #保留标签
clf=KMeans(n_clusters=3)    #设置类别为3的聚类器
model=clf.fit(X)    #训练模型
predicted=model.predict(X)    #预测每个样本所属的类别
#将预测值与标签真值进行对比
print('the predicted result:\n',predicted)
print("the real answer:\n",y)

在这里插入图片描述

3.2 自编写方式实现K-Means聚类

除了使用SKlearn的cluster模块来实现K-Means聚类外,还可以根据实际问题采用自编写的方式来实现K-Means聚类。
例:假设某物流公司要给城市的50个客户配送货物。假设公司只有5辆货车,客户的地理坐标在testSet.txt文件中,如何进行车辆分配使得配送效率最高?
问题分析:可以使用K-Means 算法,将文件内的地址数据聚成5类,由于每类的各户地址相近,则可以分配给同一辆货车。

from numpy import *
from matplotlib import pyplot as plt    
#计算两个向量的欧式距离
def distEclud(vecA, vecB):return sqrt(sum(power(vecA - vecB, 2)))
#选K个点作为初始中心点   
def initCenter(dataSet, k):print('2.初始化中心点...')shape=dataSet.shapen = shape[1]  #数据集列数    classCenter = array(zeros((k,n)))  #数组保存中心点信息,k行n列#取数据集中前k个数据点作为初始聚类中心for j in range(n):        firstK=dataSet[:k,j]classCenter[:,j] = firstKreturn classCenter#实现K-Means算法   
def myKMeans(dataSet,k):m = len(dataSet)                 #数据集行数,即样本点个数    clusterPoints = array(zeros((m,2)))   #使用clusterPoints保存数据点所属的簇序号以及距离,预设为(0,0)classCenter = initCenter(dataSet, k)  #调用initCenter函数进行各簇中心初始化clusterChanged = True  #用True和False表示是否要重新执行聚类的过程print('3.数据点距离计算以及簇的分配...')while clusterChanged:     #重复计算,直到簇分配不再变化clusterChanged = False#将每个数据点分配到最近的簇for i in range(m):   minDist = inf  #首先定义一个无穷大的值作为最近距离minIndex = -1  #预设最近的簇的序号为-1for j in range(k):distJI = distEclud(classCenter[j,:],dataSet[i,:])if distJI < minDist:  #如果样本点到某个簇的距离小于minDist,则将最近距离minDist以及所属簇的序号进行替换minDist = distJI; minIndex = jif clusterPoints[i,0] != minIndex:  #如果第i个点所属的簇序号发生了改变clusterChanged = True  #取值为True,表示要重新进行距离计算以及簇的分配,只有当所有点的簇序号不再更新时,则不在执行此过程clusterPoints[i,:] = minIndex,minDist**2  #对每个点所属的的簇序号以及距离进行更新#重新计算簇中心   for cent in range(k):#nonzero获得数据中满足条件的的元素位置下标并返回一个数组,[0]表示将数据行数单独提取出来,ptsInClust即保存了属于每个簇的数据ptsInClust = dataSet[nonzero(clusterPoints[:,0]==cent)[0]]  classCenter[cent,:] = mean(ptsInClust, axis=0)return classCenter, clusterPoints
#显示聚类结果    
def show(dataSet, k, classCenter, clusterPoints):   print('4.导入地图...')fig = plt.figure()#定义添加到图片中子区域的左下角坐标,宽度、高度rect=[0.1,0.1,1.0,1.0]axprops = dict(xticks=[], yticks=[])ax0=fig.add_axes(rect, label='ax0', **axprops)  #axprops用于接收刻度值imgP = plt.imread('city.png')#在相同区域添加axes,后面添加的axes会把前面添加的axes覆盖ax0.imshow(imgP)ax1=fig.add_axes(rect, label='ax1', frameon=False)  #frameon=False表示不显示边框print('5.聚类结果的展示...')numSamples = len(dataSet)   #对象数量mark = ['ok', '^b', 'om', 'og', 'sc']  #根据每个对象的坐标绘制点for i in range(numSamples): #因此保存的所属簇的序号不是正整数,所以先对标签进行转换markIndex = int(clusterPoints[i, 0])%k  ax1.plot(dataSet[i, 0], dataSet[i, 1], mark[markIndex])  #标记每个簇的中心点    for i in range(k):  markIndex = int(clusterPoints[i, 0])%k         ax1.plot(classCenter[i, 0], classCenter[i, 1], '^r', markersize = 12)  plt.show()print('1.导入数据...')
dataSet=loadtxt('testSet.txt')
K=5   #类的数量
classCenter,classPoints= myKMeans(dataSet,K)
show(dataSet,K,classCenter,classPoints)

在这里插入图片描述

4、算法不足与解决思路

K-Means算法过程简单,实现便捷,但是该算法也存在一定的问题。

4.1 存在的问题

1、k值较难确定
大多时候并不知道数据集应该分成多少类。实际使用时,类的数量可以是经验值,也可以多次处理选取其中最优的值,或者通过类的合并或分裂得到。
2、初始聚类中心的选择对聚类结果有较大影响
例如刚刚采用自编写方式实现K-Means聚类的例子中,初始聚类中心选择的是前k个,如果将初始聚类中心修改为中间k个、后k个或者任意的k个值,所得到的结果是不同的。也就是说,初始值选择的好坏是关键性的因素,这也是K-Means 算法的一个主要问题。
3、K-Means 算法的时间开销比较大
由于算法需要重复进行计算和样本归类,又反复调整聚类中心,因此算法的时间复杂度较高。尤其当数据集比较大时,将耗费很多时间。
4、K-Means 算法的功能具有局限性
由于算法是基于距离进行分配的,当数据包含明确分开的几部分时,可以良好地划分,然而,如果数据集形状较为复杂,比如是相互存在环绕的数据集,K-Means算法就难以处理了。

4.2 常见K值确定方法

前面存在的问题主要还是存在k值的确定上,目前研究人员提出了许多确定k值的方法,常见的几种方法如下:
1、经验值
在实际问题中,大部分的样本都只会被划分成数量较少、明确的类别,因此很多时候人们会根据经验来确定k值。
2、观测值
在聚类之前,可以用绘图方法将数据集可视化,然后通过观察,人工决定将样本聚成几类。
3、肘部方法
肘部方法(Elbow Method)是将不同的模型参数与得到的结果可视化,例如拟合出折线,帮助数据分析人员选择最佳参数。
如果不同的参数对算法结果有影响,则折线图会发生变化。例如,折线图会出现拐点,类似于手臂上的“肘部”,则表示拐点位置为模型参数的关键。
4、性能指标法
通过性能指标来确定k值,例如,选取能使轮廓系数(聚类评估的方法,值越大聚类效果越好)最大的k值。

4.3 算法评估优化思路

为了进一步提高聚类效果,可以在聚类之后再进行后期处理。例如,可以对聚类结果进行评估,根据评估进行类的划分或合并。
评价聚类算法可以使用误差值,常用的评价聚类效果的指标是误差平方和SSE。SSE 的计算比较简单,统计每个点到所属的簇中心的距离的平方和。假设n代表该簇内的数据点的个数,y’表示该簇数据点的平均值,簇的误差平方和SSE 的计算公式如下:
在这里插入图片描述
SSE值越小,表明该簇的离散程度越低,聚类效果越好。可以根据SSE值对生成的簇进行后处理,例如,将SSE值偏大的簇进行再次划分。
在K-Means算法中,由于算法收敛到局部最优,因此不同的初始值会产生不同的聚类结果。针对这个问题,使用误差值进行后处理后,离散程度高的类被拆分,得到的聚类结果更为理想。
除了在聚类之后进行处理,也可以在聚类的主过程中使用误差进行簇划分,比如常用的二分 K-Means 聚类算法。
二分K-Means 聚类的思路是首先将所有数据点看作一个簇,然后将该簇一分为二,计算每个簇内的误差指标(如SSE值),将误差最大的簇再划分成两个簇,降低聚类误差,之后不断重复进行,直到簇的个数等于用户指定的k值为止。由此思路可以看出,二分K-Means算法能够在一定程度上解决K-Means收敛于局部最优的问题。

自编写方式实现K-Means聚类物流配送问题源码及数据集

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/206642.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

浅谈WPF之控件拖拽与拖动

使用过office的visio软件画图的小伙伴都知道&#xff0c;画图软件分为两部分&#xff0c;左侧图形库&#xff0c;存放各种图标&#xff0c;右侧是一个画布&#xff0c;将左侧图形库的图标控件拖拽到右侧画布&#xff0c;就会生成一个新的控件&#xff0c;并且可以自由拖动。那如…

1 接口测试介绍

在软件测试工作中&#xff0c;接口测试是必不可少的。接口测试一般是发生在单元测试之后&#xff0c;系统测试之前。当开发人员输出API文档后&#xff0c;测试人员就可以开始编写接口测试用例了。接口测试可以让测试人员更早的介入&#xff0c;不需要等待前后端联调完成才开始测…

银行卡二要素API的应用案例:从在线购物到金融投资

引言 随着互联网技术的不断发展&#xff0c;人们的金融需求也在不断增加。随之而来的是各种新型金融服务的涌现&#xff0c;让用户的金融体验更加便利快捷。其中&#xff0c;银行卡二要素API的应用&#xff0c;则为用户的金融体验和安全性提供了极大的保障。 银行卡二要素API…

知识蒸馏的蒸馏损失方法代码总结(包括:基于logits的方法:KLDiv,dist,dkd等,基于中间层提示的方法:)

有两种知识蒸馏方法&#xff1a;一种利用教师模型的输出概率&#xff08;基于logits的方法&#xff09;[15,14,11]&#xff0c;另一种利用教师模型的中间表示&#xff08;基于提示的方法&#xff09;[12,13,18,17]。基于logits的方法利用教师的输出作为辅助信号来训练一个较小的…

【STM32】TIM定时器输出比较

1 输出比较 1.1 输出比较简介 OC&#xff08;Output Compare&#xff09;输出比较&#xff1b;IC&#xff08;Input Capture&#xff09;输入捕获&#xff1b;CC&#xff08;Capture/Compare&#xff09;输入捕获和输出比较的单元输出比较可以通过比较CNT与CCR寄存器值&#…

JavaWeb-HTTP协议

1. 什么是HTTP协议 HTTP超文本传输协(Hyper Text transfer protocol)&#xff0c;是一种用于用于分布式、协作式和超媒体信息系统的应用层协议。它于1990年提出&#xff0c;经过十几年的使用与发展&#xff0c;得到不断地完善和扩展。HTTP 是为 Web 浏览器与 Web 服务器之间的…

AI自动生成代码工具

AI自动生成代码工具是一种利用人工智能技术来辅助或自动化软件开发过程中的编码任务的工具。这些工具使用机器学习和自然语言处理等技术&#xff0c;根据开发者的需求生成相应的源代码。以下是一些常见的AI自动生成代码工具&#xff0c;希望对大家有所帮助。北京木奇移动技术有…

HCIP —— BGP 基础 (上)

BGP --- 边界网关协议 &#xff08;路径矢量协议&#xff09; IGP --- 内部网关协议 --- OSPF RIP ISIS EGP --- 外部网关协议 --- EGP BGP AS --- 自治系统 由单一的组织或者机构独立维护的网络设备以及网络资源的集合。 因 网络范围太大 需 自治 。 为区分不同的AS&#…

vim常见操作

vim常见操作 文章目录 vim常见操作1. 回退/前进2. 搜索3. 删除4. 定位到50行5. 显示行号6. 复制粘贴7. 剪贴8. 替换9. vim打开文件的时候出现 1. 回退/前进 1.esc进入命令模式 2.ctrlr 前进 u 回退2. 搜索 1&#xff09; esc进入命令模式 2&#xff09; /text  查找text&am…

【STM32】TIM定时器输入捕获

1 输入捕获 1.1 输入捕获简介 IC&#xff08;Input Capture&#xff09;输入捕获 输入捕获模式下&#xff0c;当通道输入引脚出现指定电平跳变时&#xff08;上升沿/下降沿&#xff09;&#xff0c;当前CNT的值将被锁存到CCR中&#xff08;把CNT的值读出来&#xff0c;写入到…

类风湿性关节炎口腔黏膜破裂引发抗瓜氨酸细菌和人蛋白抗体反应

今天给同学们分享一篇实验文章“Oral mucosal breaks trigger anti-citrullinated bacterial and human protein antibody responses in rheumatoid arthritis”&#xff0c;这篇文章发表在Sci Transl Med期刊上&#xff0c;影响因子为17.1。 结果解读&#xff1a; 口腔黏膜破…

Redis主从复制的配置和实现原理

Redis的持久化功能在一定程度上保证了数据的安全性&#xff0c;即便是服务器宕机的情况下&#xff0c;也可以保证数据的丢失非常少。通常&#xff0c;为了避免服务的单点故障&#xff0c;会把数据复制到多个副本放在不同的服务器上&#xff0c;且这些拥有数据副本的服务器可以用…

如何快速构建知识服务平台,打造个人或企业私域流量

随着互联网的快速发展&#xff0c;传统的知识付费平台已经不能满足用户的需求。而SaaS知识付费小程序平台则是一种新型的知识付费方式&#xff0c;具有灵活、便捷、高效等特点&#xff0c;为用户提供了更加优质的付费知识服务。本文将介绍如何搭建自己的SaaS知识付费小程序平台…

如何掌握构建 LMS 网站的艺术

目录 什么是学习管理系统 (LMS) 在线课程和 LMS 网站的好处 为什么 WordPress 对于 LMS 网站很重要 统一学习中心 多功能性和可扩展性 提高教育参与度 简化管理和监控 节省时间和费用 技能评估和绩效监督 持续学习和技能提升 使用 WordPress 插件构建成功的 LMS 课程 专注于您的…

sparkc程序idea调试提示内存不足

报错如下&#xff1a; Exception in thread "main" java.lang.IllegalArgumentException: System memory 259522560 must be at least 471859200. Please increase heap size using the --driver-memory option or spark.driver.memory in Spark configuration. 测…

自动驾驶:传感器初始标定

手眼标定 机器人手眼标定AxxB&#xff08;eye to hand和eye in hand&#xff09;及平面九点法标定 Ax xB问题求解&#xff0c;旋转和平移分步求解法 手眼标定AXXB求解方法&#xff08;文献总结&#xff09; 基于靶的方法 相机标定 (1) ApriTag (2) 棋盘格&#xff1a;cv::f…

富时中国A50指数暴跌

近年来&#xff0c;中国股市的波动一直备受关注&#xff0c;而富时中国A50指数更是其中一项备受瞩目的指标之一。然而&#xff0c;近期却出现了一场引人瞩目的暴跌&#xff0c;引发了广泛的关注和讨论。 富时中国A50指数简介 富时中国A50指数&#xff0c;作为富时罗素指数系列…

全新UI彩虹外链网盘系统源码V5.5/支持批量封禁+优化加载速度+用户系统与分块上传

源码简介&#xff1a; 全新UI彩虹外链网盘系统源码V5.5&#xff0c;它可以支持批量封禁优化加载速度。新增用户系统与分块上传。 彩虹外链网盘&#xff0c;作为一款PHP网盘与外链分享程序&#xff0c;具备广泛的文件格式支持能力。它不仅能够实现各种格式文件的上传&#xff…

CLASS60 DM蓝牙5.2双模热插拔PCB

键盘使用说明索引&#xff08;均为出厂默认值&#xff09; 软件支持&#xff08;驱动的详细使用帮助&#xff09;一些常见问题解答&#xff08;FAQ&#xff09;首次使用步骤蓝牙配对规则&#xff08;重要&#xff09;蓝牙和USB切换键盘默认层默认触发层0的FN键配置的功能默认功…

使用word中的VBA 批量设置Word中所有图片大小

在VBA编辑器中&#xff0c;你可以创建、编辑和运行VBA宏代码&#xff0c;以实现自动化任务和自定义Word 功能。如果你是VBA编程初学者&#xff0c;可以在VBA编辑器中查看Word VBA宏代码示例&#xff0c;以便更好地了解如何使用VBA编写代码。 要打开VBA编辑器&#xff0c;你可以…