k-均值聚类算法

  • 一、实验目的
  • 二、实验原理
    • 1、k-均值聚类
    • 2、终止条件
  • 三、实验内容和步骤
    • 1、实验内容
    • 2、实验步骤
    • 3、程序框图
    • 4、实验样本
    • 5、实验代码
  • 四、实验结果
  • 五、实验分析

一、实验目的

  1. 熟悉k-均值聚类算法。
  2. 在训练样本集上编写用于 k-均值聚类的程序,对任务相关数据运行 k-均值聚类算法,调试实验。
  3. 掌握距离计算方法和聚类的评价准则。
  4. 写出实验报告。

二、实验原理

1、k-均值聚类

k-均值聚类是一种基于形心的划分技术,具体迭代的计算步骤如下:

  1. 在属性向量空间随机产生k个形心坐标。
  2. 分别计算数据集 D 中的每个数据对象 Ti(1≤i≤n)T_i (1\leq i\leq n)Ti​(1≤i≤n)到所有kkk个形心的距离度量 Dist(i,j)(1≤i≤n,1≤j≤k)Dist(i,j) (1\leq i\leq n, 1\leq j\leq k)Dist(i,j)(1≤i≤n,1≤j≤k),并将数据对象 TiT_iTi​ 聚到最小距离度量的那一簇中。即 Ti∈CJT_i\in C_JTi​∈CJ​,表示数据对象TiT_iTi​被聚到第JJJ簇中。其中J=arg min⁡(Dist(i,j))J=\argmin(Dist(i,j))J=argmin(Dist(i,j)),表示JJJ为可使得Dist(i,j)Dist(i,j)Dist(i,j)取最小值的那个jjj。
  3. 按照形心的定义计算每一簇的形心坐标,形成下一代的kkk个形心坐标。
  4. 如果不满足终结条件,转到 2)继续迭代;否则结束。

其中,簇的形心可以有不同的的定义,例如可以是簇内数据对象属性向量的均值(也就是重心),也可以是中心点等;距离度量也可以有不同的定义,常用的有欧氏距离、曼哈顿(或城市块、街区)距离、闵可夫斯基距离等;终结条件可采用当对象的重新分配不再发生时,程序迭代结束。

2、终止条件

终止条件可以是以下任何一个:

  1. 没有(或最小数目)对象被重新分配给不同的聚类。
  2. 没有(或最小数目)聚类中心再发生变化。
  3. 误差平方和局部最小。

三、实验内容和步骤

1、实验内容

  1. 根据 k-均值聚类算法的计算步骤,画出 k=3 时的程序流程图;
  2. 由 k-均值程序流程图编程实现 k-均值聚类算法;
  3. 在实验报告中显示 k-均值聚类过程的一系列截图,指明各个簇的逐渐演
    化过程;
  4. 在报告中指出实验代码中的初始质心的选择,终止条件的选择,以及距
    离度量的选择并予以说明。

2、实验步骤

编程实现如下功能:

  1. 首先将数据集 D={D1,D2,D3}中的属性向量作为实验数据输入;
  2. 由 k-均值程序流程图编程实现 k-均值聚类算法,并用实验数据运行;
  3. 运行过程中在适当的迭代代数暂停并显示实时迭代的结果,如簇心的位
    置、按距离最近邻聚类的结果等;

3、程序框图


程序框图

4、实验样本

data.txt

5、实验代码

#!/usr/bin/env python  
# -*- coding: utf-8 -*-
#
# Copyright (C) 2021 #
# @Time    : 2022/5/30 21:29
# @Author  : Yang Haoyuan
# @Email   : 2723701951@qq.com
# @File    : Exp5.py
# @Software: PyCharm
import math
import random
import argparseimport numpy as np
import matplotlib.pyplot as plt
from sklearn.metrics import calinski_harabasz_scoreparser = argparse.ArgumentParser(description="Exp5")
parser.add_argument("--epochs", type=int, default=100)
parser.add_argument("--k", type=int, default=3)
parser.add_argument("--n", type=int, default=2)
parser.add_argument("--dataset", type=str, default="data.txt")parser.set_defaults(augment=True)
args = parser.parse_args()
print(args)# 读取数据集
def loadDataset(filename):dataSet = []with open(filename, 'r') as file_to_read:while True:lines = file_to_read.readline()  # 整行读取数据if not lines:breakp_tmp = [str(i) for i in lines.split(sep="\t")]p_tmp[len(p_tmp) - 1] = p_tmp[len(p_tmp) - 1].strip("\n")for i in range(len(p_tmp)):p_tmp[i] = float(p_tmp[i])dataSet.append(p_tmp)return dataSet# 计算n维数据间的欧式距离
def euclid(p1, p2, n):distance = 0for i in range(n):distance = distance + (p1[i] - p2[i]) ** 2return math.sqrt(distance)# 初始化聚类中心
def init_centroids(dataSet, k, n):_min = dataSet.min(axis=0)_max = dataSet.max(axis=0)centre = np.empty((k, n))for i in range(k):for j in range(n):centre[i][j] = random.uniform(_min[j], _max[j])return centre# 计算每个数据到每个中心点的欧式距离
def cal_distance(dataSet, centroids, k, n):dis = np.empty((len(dataSet), k))for i in range(len(dataSet)):for j in range(k):dis[i][j] = euclid(dataSet[i], centroids[j], n)return dis# K-Means聚类
def KMeans_Cluster(dataSet, k, n, epochs):epoch = 0# 初始化聚类中心centroids = init_centroids(dataSet, k, n)# 迭代最多epochswhile epoch < epochs:# 计算欧式距离distance = cal_distance(dataSet, centroids, k, n)classify = []for i in range(k):classify.append([])# 比较距离并分类for i in range(len(dataSet)):List = distance[i].tolist()# 因为初始中心的选取完全随机,所以存在第一次分类,类的数量不足k的情况# 这里作为异常捕获,也就是distance[i]=nan的时候,证明类的数量不足# 则再次递归聚类,直到正常为止,返回聚类标签和中心点try:index = List.index(distance[i].min())except:labels, centroids = KMeans_Cluster(dataSet=np.array(data_set), k=args.k, n=args.n, epochs=args.epochs)return labels, centroidsclassify[index].append(i)# 构造新的中心点new_centroids = np.empty((k, n))for i in range(len(classify)):for j in range(n):new_centroids[i][j] = np.sum(dataSet[classify[i]][:, j:j + 1]) / len(classify[i])# 比较新的中心点和旧的中心点是否一样if (new_centroids == centroids).all():# 中心点一样,停止迭代label_pred = np.empty(len(data_set))# 返回个样本聚类结果和中心点for i in range(k):label_pred[classify[i]] = ireturn label_pred, centroidselse:centroids = new_centroidsepoch = epoch + 1# 聚类结果展示
def show(label_pred, X, centroids):x = []for i in range(args.k):x.append([])for k in range(args.k):for i in range(len(label_pred)):_l = int(label_pred[i])x[_l].append(X[i])for i in range(args.k):plt.scatter(np.array(x[i])[:, 0], np.array(x[i])[:, 1], color=plt.cm.Set1(i % 8), label='label' + str(i))plt.scatter(x=centroids[:, 0], y=centroids[:, 1], marker='*', label='pred_center')plt.legend(loc=3)plt.show()if __name__ == "__main__":# 读取数据data_set = loadDataset(args.dataset)# 原始数据展示plt.scatter(np.array(data_set)[:, :1], np.array(data_set)[:, 1:])plt.show()# 获取聚类结果labels, centroids = KMeans_Cluster(dataSet=np.array(data_set), k=args.k, n=args.n, epochs=args.epochs)print("Classes: ", labels)print("Centers: ", centroids)# 使用Calinski-Harabaz标准评价聚类结果scores = calinski_harabasz_score(data_set, labels)print("Scores: ", round(scores, 2))# 展示聚类结果show(X=np.array(data_set), label_pred=labels, centroids=centroids)

四、实验结果


原始数据分布散点图

一种“好”聚类后分类情况散点图以及聚类中心

一种“好”聚类后聚类标签,聚类中心和CH指数得分情况

一种“坏”聚类后分类情况散点图以及聚类中心

一种“坏”聚类后聚类标签,聚类中心和CH指数得分情况

五、实验分析

本次实验主要是K-Means算法的实现。

对于样本之间的距离,我采用欧几里得距离度量,这是在经典K-Means算法中已经被证明是高度有效的相似性和非相似性度量标准。

我将聚类中心不再变化或者迭代次数达到上限作为终止条件,放着某些不收敛的情况造成的程序运行时间过长。

由于聚类中心的初始选取完全随机,所以可能出现第一次聚类类的数量小于规定的k的情况,对于这种情况,我在异常处理中直接进行递归,重新开始聚类,返回递归聚类结果。同时,由于聚类中心的随机性,即使针对同一数据集,在参数相同的情况下,其聚类结果有可能存在巨大差距。为了评判聚类结果的“好”或“坏”,我使用Calinski−Harabaz(CH)Calinski-Harabaz(CH)Calinski−Harabaz(CH)标准评价聚类结果。这是一种经典的算法,用以评价类间和类内部的协方差,进而评价聚类结果。较之于Silhouettes指数,CH指数的计算更加快捷。其计算公式如下:
CH=BGSSk−1/WGSSn−kCH=\frac{BGSS}{k-1} / \frac{WGSS}{n-k} CH=k−1BGSS​/n−kWGSS​
BGSS指类间协方差,WGSS指类内协方差。一个好的聚类应当具有较大的类间协方差和较小的类内协方差,从而使得CH指数达到局部或者全局的最大值。从实验结果可以看出,在经验上更好的聚类结果确实具有更大的CH得分。

河北工业大学数据挖掘实验五 k-means聚类算法相关推荐

  1. 河北工业大学数据挖掘实验一 数据预处理

    河北工业大学数据挖掘实验一 数据预处理 一.实验目的 二.实验原理 1.数据预处理 2.数据清理 3.数据集成 4.数据变换 5.数据归约 三.实验内容和步骤 1.实验内容 2.实验步骤 3.程序框图 ...

  2. 河北工业大学数据挖掘实验三 应用 Apriori 算法挖掘频繁项集

    河北工业大学数据挖掘实验三 应用 Apriori 算法挖掘频繁项集 一.实验目的 二.实验原理 1.Apriori 算法 2.提高频繁项集逐层产生的效率 三.实验内容和步骤 1.实验内容 2.实验步骤 ...

  3. 河北工业大学数据挖掘实验四 贝叶斯决策分类算法

    贝叶斯决策分类算法 一.实验目的 二.实验原理 1.先验概率和类条件概率 2.贝叶斯决策 三.实验内容和步骤 1.实验内容 2.实验步骤 3.程序框图 4.实验样本 5.实验代码 四.实验结果 五.实 ...

  4. k means聚类算法_一文读懂K-means聚类算法

    1.引言 什么是聚类?我们通常说,机器学习任务可以分为两类,一类是监督学习,一类是无监督学习.监督学习:训练集有明确标签,监督学习就是寻找问题(又称输入.特征.自变量)与标签(又称输出.目标.因变量) ...

  5. k means聚类算法_K-Means 聚类算法 20210108

    说到聚类,应先理解聚类和分类的区别 聚类和分类最大的不同在于:分类的目标是事先已知的,而聚类则不一样,聚类事先不知道目标变量是什么,类别没有像分类那样被预先定义出来. K-Means 聚类算法有很多种 ...

  6. OpenCV官方文档 理解k - means聚类

    理解k - means聚类 目标 在这一章中,我们将了解k - means聚类的概念,它是如何工作等. 理论 我们将这个处理是常用的一个例子. t恤尺寸问题 考虑一个公司要发布一个新模型的t恤. 显然 ...

  7. 【模式识别】K均值聚类算法应用实验报告及MATLAB仿真

    一. 实验目的 1.掌握K均值聚类算法的原理和实现过程: 2.掌握K均值聚类算法的应用方法. 二. 实验内容 1.彩色图像分割 选择一幅图像,分别按三种颜色数进行彩色图像分割的结果(原图和分割图).步 ...

  8. OpenCV的k - means聚类 -对图片进行颜色量化

    OpenCV的k - means聚类 目标 学习使用cv2.kmeans()数据聚类函数OpenCV 理解参数 输入参数 样品:它应该的np.float32数据类型,每个特性应该被放在一个单独的列. ...

  9. Thinking in SQL系列之五:数据挖掘K均值聚类算法与城市分级

    原创: 牛超   2017-02-21   Mail:10867910@qq.com 引言:前一篇文章开始不再介绍简单算法,而是转到数据挖掘之旅.感谢CSDN将我前一篇机器学习C4.5决策树算法的博文 ...

最新文章

  1. Foreach与Random
  2. ubuntu jdk
  3. OpenCV图像处理——判断图像是否失焦模糊
  4. 【Java报错】mapper传入array\collection\list类型的参数时报BindingException:Parameter `` not found(问题复现+3种解决方法)
  5. ExceptionLess新玩法 — 记日志
  6. 截取AVI格式的视频C语言代码
  7. TCP 从客户端键入信息 循环接收发送 示例
  8. 【从 0 开始机器学习】手把手用 Python 实现梯度下降法!
  9. 工科数学分析之数学感悟
  10. 无线桥接:没有网口解决nas有线组网问题
  11. DedeCMS二次开发 - 文件结构了解
  12. flappy brid
  13. 笔记本显卡和台式显卡区别介绍
  14. JAVA计算机毕业设计医院药品管理系统Mybatis+源码+数据库+lw文档+系统+调试部署
  15. 大数据系列(一)之hadoop介绍及集群搭建
  16. cloud-init 数据获取处理文档
  17. 神探夏洛克 | 不再卖腐,第四季的最大的看点变成了……
  18. python读xml文件生成.h头文件_Python创建xml文件示例
  19. 美国计算机专业博士后,美国俄克拉荷马大学电子与计算机工程系招聘博士后
  20. java线程调度(优先级,休眠,让步,等待)

热门文章

  1. 06-图1 列出连通集 —— 非联通图的DFS与BFS
  2. java教材管理系统,基于web的教材管理系统
  3. 东方甄选爆火背后的流量密码
  4. 优秀的flash站点收集(30+)
  5. 深度学习入门之python读取图片转化为向量
  6. 美国亚利桑那州成立自动驾驶移动研究所,研发无人车技术
  7. FreeRTOS嵌入式实时操系统查看指定任务剩余堆栈大小方法
  8. 阿里/腾讯云静默安装Oracle11G超级详细教程
  9. 支付宝公众服务接口和微信公众平台接口的区别
  10. 牛客wannafly27 C 树形dp