有两个月的时间没有更新博客了。最近很忙,中断了机器学习的学习。这两天又把这本书拿出来接着看,SVM还是没有看明白,索性就看了个简单的K-均值聚类。
1、聚类定义:聚类是一种无监督学习(也就是在聚类结果出来之前我们不知道每个簇是什么),它将相似的对象归为一类,和我们常说的“人以群分,物以类聚”是相似的。
在学习K个好邻居的时候说过数据挖掘的流程,这里再次回忆一下:
2、开发机器学习应用程序的步骤
(1)收集数据:收集各种样本数据,为了节省时间,可以使用公开的可用数据源
(2)准备输入数据:确保数据格式符合要求,本书采用的格式是Python语言的List。
(3)数据分析:人工分析以前得到的数据,确保数据集中没有垃圾数据。
(4)训练算法,这一步才是机器学习真正的开始,对于监督学习,我们把之前的格式化数据输入到算法中,得到分类模型,方便后续处理。对于无监督学习,不存在目标变量,因此也不需要训练算法!!!
(5)测试算法:这一步使用第4步机器学习的模型。这一步主要测试算法的工作效率。
(6)使用算法:将机器学习算法转换为应用程序,执行实际任务。
3、K-均值聚类
首先,随机确定k个初始点作为质心。然后为每个点找距离其最近的质心,将其分配到该质心所对应的簇中。完成这一步之后,更新每个簇的质心为该簇所有点的平均值。迭代以上过程,直到簇分配结果不再改变,完成K-均值聚类。
伪代码:很重要!!!代表着算法的逻辑
随机创建K个质心为起始点 当任意一个点的簇分配结果发生变化时 对每一个数据点 对每个质心 计算数据点和之心之间的距离 将数据点分配到距离最近的簇中 对每个簇,计算所有点的均值更新质心
4、算法的实现
(1)创建文件kMeans.py,编写k-均值算法需要用到的通用函数,代码如下:
from numpy import * #加载数据集 def loadDataSet(fileName): dataMat=[] fr=open(fileName) for line in fr.readlines(): curLine=line.strip().split('\t') #map函数的主要功能是 #对一个序列对象中的每一个元素应用被传入的函数,并且返回一个包含了所有函数调用结果的一个列表 #这里从文件中读取的信息是字符型,通过map函数将其强制转化为浮点型 frtLine=map(float,curLine) dataMat.append(frtLine) return dataMat #计算两个向量之间的距离 def distEclud(vecA,vecB): return sqrt(sum(power(vecA-vecB,2))) #随机构建初始质心 def randCent(dataSet,k): #数据列数 n=shape(dataSet)[1] #初始化质心 centroids=mat(zero(k,n)) for j in range(n): #求每一维数据的最大值和最小值,保证随机选取的质心在边界之内 minJ=min(dataSet[:,j]) maxJ=max(dataSet[:,j]) rangeJ=float(maxJ-minJ) centroids[:,j]=minJ+rangeJ*random.rand(k,1) return centroids
对上面的随机选点函数进行测试:
有了以上的通用函数,我们就可以实现k-均值算法了,具体的算法如下:
#kMeans算法 def kMeans(dataSet,k,distMeas=distEclud,createCent=randCent): #数据点的行数 m=shape(dataSet)[0] #用于记录数据点到之心的距离平方 clusterAssment=mat(zeros((m,2))) #中心点 centroids=createCent(dataSet,k) #聚类结束标志 clusterChanged=True while clusterChanged: clusterChanged=False; #遍历每条数据 for i in range(m): #设置两个变量,分别存放数据点到质心的距离,及数据点属于哪个质心 minDist=inf;minIndex=-1; #遍历每个质心 for j in range(k): distJI=distMeas(centroids[j,:],dataSet[i,:]) if(distJI<minDist): #将数据归为最近的质心 minDist=distJI;minIndex=j; #簇分配结果发生变化,更新标志 if clusterAssment[i,0]!=minIndex:clusterChanged=True clusterAssment[i,:]=minIndex,minDist**2 print centroids #更新质心 for cent in range(k): ptsInClust=dataSet[nonzero(clusterAssment[:,0].A==cent)[0]] centroids[cent,:]=mean(ptsInClust,axis=0) return centroids,clusterAssment
测试结果如下:
经过三次迭代,找到了4个合适的质心。
这样我们就完成了k-均值算法的实现,那么我们如何知道我们生成的簇结果是比较好的呢?我们通过点到簇新的平方和来估计结果的好坏,即通过误差平方和SSE(Sum of SquaredError)来度量。由于sse并不是一个凸函数,我们使用K-means算法有些情况下得到的局部最小值,并不是最有的聚类结果。为了改善这种局部最优的缺点,可以通过多次执行k-means算法,找到使得SSE最小的聚类。另一种方法就是有人提出了二分k-均值算法。
5、二分K-均值
该算法首先将所有的点当成一个簇,然后将该簇一分为二。之后选择其中一个簇进行划分,选择哪一个簇进行划分取决于对其划分是否可以最大程度降低SSE的值。不断重复该过程,直到达到用户所需要的簇个数为止。
将所有的点看成一个簇 当簇数目小于k时 对每一个簇 计算总误差 在给定的簇上面进行二分k-均值聚类 计算一分为二之后的总误差 选择使得误差最小的那个簇进行划分
编写代码如下:
def biKmeans(dataSet,k,distMeas=distEclud): m=shape(dataSet)[0] clusterAssment=mat(zeros((m,2))) #创建一个初始簇 centroid0=mean(dataSet,axis=0).tolist()[0] centList=[centroid0] #计算初始误差 for j in range(m): clusterAssment[j,1]=distMeas(mat(centroid0),dataSet[j,:])**2 while(len(centList)<k): lowestSSE=inf #遍历每个簇,尝试划分每个簇 for i in range(len(centList)): ptsInCurrCluster=\ dataSet[nonzero(clusterAssment[:,0].A==i)[0],:] centroidMat,splitClustAss=\ kMeans(ptsInCurrCluster,2,distMeas) #划分后的误差平方和 sseSplit=sum(splitClustAss[:,1]) #剩余的误差之和 sseNotSplit=\ sum(clusterAssment[nonzero(clusterAssment[:,0].A!=i)[0],1]) print "ssesplit,sseNotSplit",sseSplit,sseNotSplit if(sseSplit+sseNotSplit)<lowestSSE: bestCentToSplit=i bestNewCents=centroidMat bestClustAss=splitClustAss.copy() lowestSSE=sseSplit+sseNotSplit #更新分配结果 bestClustAss[nonzero(bestClustAss[:,0].A==1)[0],0]=\ len(centList) bestClustAss[nonzero(bestClustAss[:,0].A==0)[0],0]=\ bestCentToSplit print "the bestCentToSplit is:",bestCentToSplit print "the len of bestClustAss is:",len(bestClustAss) centList[bestCentToSplit]=bestNewCents[0,:] centList.append(bestNewCents[1,:]) clusterAssment[nonzero(clusterAssment[:,0].A==\ bestCentToSplit)[0],:]=bestClustAss print centList return mat(centList),clusterAssment
相关推荐
总结,K-均值聚类算法是一种基础而实用的机器学习技术,它在解决许多实际问题时展现出了强大的能力。然而,我们也应意识到其局限性,并考虑采用其他聚类方法或对其进行优化,以适应复杂的数据分布和业务需求。
在数据分析和机器学习领域,聚类是一种常用的技术,用于无监督地将数据点分组到不同的类别中。k-means聚类算法是其中最简单且广泛使用的算法之一,尤其适用于处理大规模数据集。本篇文章将深入探讨如何在Matlab环境...
### 机器学习第十三讲:K-均值算法 #### 一、引言与背景 在机器学习领域中,无监督学习(Unsupervised Learning)是处理未标记数据的一种重要方法。与有监督学习不同,无监督学习并不依赖于已知的结果或类别标签来...
《Matlab实现C-均值动态聚类算法详解...总之,C-均值聚类算法在Matlab中的实现为科研和教学提供了便利,而深入理解和掌握这一算法,对于从事数据分析、机器学习以及相关领域的专业人士来说,是提升自身技能的重要一环。
在机器学习领域,它被用来发现数据集中的自然群组,无需预先知道类别信息。该算法的基本思想是通过迭代将数据点分配到最近的聚类中心,从而形成多个聚类。 **算法步骤:** 1. **初始化**:选择K个初始聚类中心,...
k-means算法是一种广泛应用的无监督机器学习方法,主要用于数据的聚类分析。它通过将数据点分配到最近的聚类中心来实现自动分组,从而揭示数据的内在结构。以下是对k-means算法及其在实战中应用的详细说明。 **一、...
K-means是一种常见的无监督机器学习算法,用于将数据集划分为K个不同的类别或簇。在图像处理领域,这种方法可以用来自动地将图像划分为多个具有相似颜色或纹理特征的区域。 首先,我们要理解K-means的工作原理。K-...
K均值聚类代码,机器学习实战K均值聚类代码,机器学习实战
此外,理解K-means聚类算法有助于扩展到其他机器学习领域,如数据挖掘和推荐系统。 K-means算法虽然简单且高效,但也存在一些局限性,例如对初始聚类中心敏感、对异常值不鲁棒、难以处理非凸形状的聚类等。在实际...
K-Means是一种非监督学习方法,广泛应用于数据挖掘和机器学习领域,用于将数据集划分为K个不同的簇。通过优化迭代过程,使得同一簇内的数据点彼此相似,而不同簇之间的数据点差异最大化。 首先,我们要理解GPU在...
机器学习实战这本书中的数据集文本。
在这个"Python——机器学习实战——K均值聚类算法分组"的教程中,我们将深入探讨如何使用Python来实现这个算法。 首先,K均值算法的核心思想是通过迭代找到最佳的K个聚类中心,使得每个数据点到其所属类别中心的...
本文实例为大家分享了python K均值聚类的具体代码,供大家参考,具体内容如下 #-*- coding:utf-8 -*- #!/usr/bin/python ''''' k Means K均值聚类 ''' # 测试 # K均值聚类 import kMeans as KM KM.kMeansTest() #...
在机器学习领域,聚类是一种无监督学习方法,主要用于发现数据集中的自然群体或类别,无需预先知道具体的分类标签。本压缩包包含针对鸢尾花数据集的三种聚类算法实现:k均值(K-Means)、合并聚类(Agglomerative ...
1. 《机器学习实战》 - K-均值聚类 2. 斯坦福 ML 公开课笔记 12——K-Means、混合高斯分布、EM 算法 总的来说,K-均值聚类是一种强大的工具,尽管存在一些局限性,但在许多实际场景下,通过适当的调整和配合其他...
"机器学习实战_Machine_Learning_in_Action.pdf" 机器学习实战是指通过实践和应用机器学习算法来解决实际问题的过程。在本书中,我们将学习机器学习的基础知识,包括k-近邻算法、决策树、基于概率论的分类方法、...
在机器学习领域,KNN(K-Nearest Neighbors)算法和C均值聚类算法(K-Means Clustering)以及BP(Backpropagation)神经网络是三种重要的技术。这些算法广泛应用于数据分类、模式识别和预测问题,对理解和实践机器...