python中实现k-means聚类算法详解


Posted in Python onNovember 11, 2017

算法优缺点:

优点:容易实现
缺点:可能收敛到局部最小值,在大规模数据集上收敛较慢
使用数据类型:数值型数据

算法思想

k-means算法实际上就是通过计算不同样本间的距离来判断他们的相近关系的,相近的就会放到同一个类别中去。

1.首先我们需要选择一个k值,也就是我们希望把数据分成多少类,这里k值的选择对结果的影响很大,Ng的课说的选择方法有两种一种是elbow method,简单的说就是根据聚类的结果和k的函数关系判断k为多少的时候效果最好。另一种则是根据具体的需求确定,比如说进行衬衫尺寸的聚类你可能就会考虑分成三类(L,M,S)等

2.然后我们需要选择最初的聚类点(或者叫质心),这里的选择一般是随机选择的,代码中的是在数据范围内随机选择,另一种是随机选择数据中的点。这些点的选择会很大程度上影响到最终的结果,也就是说运气不好的话就到局部最小值去了。这里有两种处理方法,一种是多次取均值,另一种则是后面的改进算法(bisecting K-means)

3.终于我们开始进入正题了,接下来我们会把数据集中所有的点都计算下与这些质心的距离,把它们分到离它们质心最近的那一类中去。完成后我们则需要将每个簇算出平均值,用这个点作为新的质心。反复重复这两步,直到收敛我们就得到了最终的结果。

函数

loadDataSet(fileName)

从文件中读取数据集

distEclud(vecA, vecB)

计算距离,这里用的是欧氏距离,当然其他合理的距离都是可以的

randCent(dataSet, k)

随机生成初始的质心,这里是虽具选取数据范围内的点

kMeans(dataSet, k, distMeas=distEclud, createCent=randCent)

kmeans算法,输入数据和k值。后面两个事可选的距离计算方式和初始质心的选择方式

show(dataSet, k, centroids, clusterAssment)

可视化结果

#coding=utf-8
from numpy import *
def loadDataSet(fileName):
 dataMat = []
 fr = open(fileName)
 for line in fr.readlines():
 curLine = line.strip().split('\t')
 fltLine = map(float, curLine)
 dataMat.append(fltLine)
 return dataMat
#计算两个向量的距离,用的是欧几里得距离
def distEclud(vecA, vecB):
 return sqrt(sum(power(vecA - vecB, 2)))
#随机生成初始的质心(ng的课说的初始方式是随机选K个点) 
def randCent(dataSet, k):
 n = shape(dataSet)[1]
 centroids = mat(zeros((k,n)))
 for j in range(n):
 minJ = min(dataSet[:,j])
 rangeJ = float(max(array(dataSet)[:,j]) - minJ)
 centroids[:,j] = minJ + rangeJ * random.rand(k,1)
 return centroids
def kMeans(dataSet, k, distMeas=distEclud, createCent=randCent):
 m = shape(dataSet)[0]
 clusterAssment = mat(zeros((m,2)))#create mat to assign data points 
     #to a centroid, also holds SE of each point
 centroids = createCent(dataSet, k)
 clusterChanged = True
 while clusterChanged:
 clusterChanged = False
 for i in range(m):#for each data point assign it to the closest centroid
  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):#recalculate centroids
  ptsInClust = dataSet[nonzero(clusterAssment[:,0].A==cent)[0]]#get all the point in this cluster
  centroids[cent,:] = mean(ptsInClust, axis=0) #assign centroid to mean 
 return centroids, clusterAssment
def show(dataSet, k, centroids, clusterAssment):
 from matplotlib import pyplot as plt 
 numSamples, dim = dataSet.shape 
 mark = ['or', 'ob', 'og', 'ok', '^r', '+r', 'sr', 'dr', '<r', 'pr'] 
 for i in xrange(numSamples): 
 markIndex = int(clusterAssment[i, 0]) 
 plt.plot(dataSet[i, 0], dataSet[i, 1], mark[markIndex]) 
 mark = ['Dr', 'Db', 'Dg', 'Dk', '^b', '+b', 'sb', 'db', '<b', 'pb'] 
 for i in range(k): 
 plt.plot(centroids[i, 0], centroids[i, 1], mark[i], markersize = 12) 
 plt.show()
def main():
 dataMat = mat(loadDataSet('testSet.txt'))
 myCentroids, clustAssing= kMeans(dataMat,4)
 print myCentroids
 show(dataMat, 4, myCentroids, clustAssing) 
 
if __name__ == '__main__':
 main()

这里是聚类结果,还是很不错的啦

python中实现k-means聚类算法详解

但是有时候也会收敛到局部最小值,就像下面这样,就是不幸收敛到局部最优了

python中实现k-means聚类算法详解

总结

以上就是本文关于python中实现k-means聚类算法详解的全部内容,希望对大家有所帮助。感兴趣的朋友可以继续参阅本站:

有什么问题可以随时留言,小编会及时回复大家的。感谢朋友们对本站的支持!

Python 相关文章推荐
django自定义Field实现一个字段存储以逗号分隔的字符串
Apr 27 Python
python之yield表达式学习
Sep 02 Python
Python判断文件或文件夹是否存在的三种方法
Jul 27 Python
django 发送邮件和缓存的实现代码
Jul 18 Python
对python requests发送json格式数据的实例详解
Dec 19 Python
python scp 批量同步文件的实现方法
Jan 03 Python
Python从list类型、range()序列简单认识类(class)【可迭代】
May 31 Python
Python pandas实现excel工作表合并功能详解
Aug 29 Python
Python 批量刷博客园访问量脚本过程解析
Aug 30 Python
Pytorch 保存模型生成图片方式
Jan 10 Python
Tensorflow卷积实现原理+手写python代码实现卷积教程
May 22 Python
Python3爬虫RedisDump的安装步骤
Feb 20 Python
Python编程之基于概率论的分类方法:朴素贝叶斯
Nov 11 #Python
Python内存管理方式和垃圾回收算法解析
Nov 11 #Python
Python实现的人工神经网络算法示例【基于反向传播算法】
Nov 11 #Python
python中使用正则表达式的后向搜索肯定模式(推荐)
Nov 11 #Python
python基础练习之几个简单的游戏
Nov 10 #Python
Python实现购物车功能的方法分析
Nov 10 #Python
Python实现的单向循环链表功能示例
Nov 10 #Python
You might like
随时给自己贴的图片加文字的php代码
2007/03/08 PHP
Gregarius中文日期格式问题解决办法
2008/04/22 PHP
详解Yii2高级版引入bootstrap.js的一个办法
2017/03/21 PHP
jQuery替换字符串(实例代码)
2013/11/13 Javascript
js动态创建上传表单通过iframe模拟Ajax实现无刷新
2014/02/20 Javascript
javascript基本算法汇总
2016/03/09 Javascript
微信小程序  自定义创建详细介绍
2016/10/27 Javascript
vue一步步实现alert功能
2017/07/05 Javascript
ES6学习教程之模板字符串详解
2017/10/09 Javascript
JavaScript模块详解
2017/12/18 Javascript
Vue+elementui 实现复杂表头和动态增加列的二维表格功能
2019/09/23 Javascript
深入浅析vue全局环境变量和模式
2020/04/28 Javascript
解决Antd Table表头加Icon和气泡提示的坑
2020/11/17 Javascript
python 查找文件夹下所有文件 实现代码
2009/07/01 Python
tensorflow 中对数组元素的操作方法
2018/07/27 Python
Pycharm设置utf-8自动显示方法
2019/01/17 Python
Django的Modelforms用法简介
2019/07/27 Python
在Python中使用turtle绘制多个同心圆示例
2019/11/23 Python
python接口自动化如何封装获取常量的类
2019/12/24 Python
python报错: 'list' object has no attribute 'shape'的解决
2020/07/15 Python
Python数据库封装实现代码示例解析
2020/09/05 Python
CSS3的Border-radius轻松制作圆角
2012/12/24 HTML / CSS
美国浴缸、水槽和水龙头购物网站:Vintage Tub & Bath
2019/11/05 全球购物
计算机毕业大学生推荐信
2013/12/01 职场文书
博士学位自我鉴定范文
2013/12/26 职场文书
车间统计员岗位职责
2014/01/05 职场文书
装修五一活动策划案
2014/01/23 职场文书
国际贸易专业个人求职信格式
2014/02/02 职场文书
《永远的白衣战士》教学反思
2014/04/25 职场文书
国际贸易实训报告
2014/11/05 职场文书
后天观后感
2015/06/08 职场文书
三八妇女节致辞
2015/07/31 职场文书
观看安全警示教育片心得体会
2016/01/15 职场文书
Angular CLI发布路径的配置项浅析
2021/03/29 Javascript
pycharm debug 断点调试心得分享
2021/04/16 Python
python缺失值填充方法示例代码
2022/12/24 Python