机器学习之非监督学习(四)K-means 聚类算法

news2024/9/20 21:39:27

机器学习之非监督学习(一)K-means 聚类算法

  • 0. 文章传送
  • 1.非监督学习定义
  • 2.非监督学习分类
    • 2.1 聚类 Clustering
    • 2.2 异常检测 Anomaly Detection
  • 3.K-means聚类算法 K-means clustering
    • 案例引入
    • 算法步骤
    • 算法优化
      • 成本函数
      • 初始化方法
      • K的选择
    • 代码实现
  • 4.案例实战:图像压缩

0. 文章传送

机器学习之监督学习(一)线性回归、多项式回归、算法优化[巨详细笔记]
机器学习之监督学习(二)二元逻辑回归
机器学习之监督学习(三)神经网络基础
机器学习之实战篇——预测二手房房价(线性回归)
机器学习之实战篇——肿瘤良性/恶性分类器(二元逻辑回归)
机器学习之实战篇——MNIST手写数字0~9识别(全连接神经网络模型)
机器学习之监督学习(四)决策树和随机森林

1.非监督学习定义

非监督学习是一种机器学习方法,在这种方法中,模型在没有预先标记的数据的情况下进行训练。相较于监督学习(需要提供输入和对应的输出标签),非监督学习仅依赖输入数据自身的结构来发现数据内部的模式和关系。


2.非监督学习分类

2.1 聚类 Clustering

聚类的目标是将数据集划分成多个组(或簇),使得簇内的数据点彼此相似,而不同簇的数据点差异较大。常见的聚类算法有 K 均值聚类(K-Means)、层次聚类和 DBSCAN 等。

2.2 异常检测 Anomaly Detection

异常检测的目标是识别数据集中与大多数数据点显著不同的异常数据点。异常检测在网络安全、金融欺诈检测等领域有广泛应用。常见的方法有孤立森林(Isolation Forest)和基于密度的检测方法等。


3.K-means聚类算法 K-means clustering

案例引入

在购买衣物时,我们通常根据自己的身高和体重来选择合适尺码的衣服,常见的衣服衣服型号标法为小(S)、中(M)、大(L)。假设某衣服生产商收集了一些用户身高和体重的数据,如果要根据这些数据点划分三个类别,该如何实现最优划分呢?这便是典型的聚类问题,如下图所示,三个圈代表三种型号,将无标签的数据划分为三个类别。下面介绍处理聚类问题的K-means算法。
在这里插入图片描述

算法步骤

K-means聚类算法步骤如下:

  1. randomly generate cluster centroids 随机产生簇心
  2. assign each point to its closest centroid 将点分配到最近的簇中
  3. recompute the centroids 重新计算簇心 (簇内的中心点)
  4. repeat step2 and step3 重复步骤2和步骤3直至簇心不再移动(或点所处簇不再改变)

在这里插入图片描述
从上面的动图可以很直观地理解算法的思想,需要注意的是,起始点选择不同,聚类的结果也不同。

用数学语言表示如下:
m 个数据, n 个特征, m 个数据分别记为 x ( 1 ) 、 x ( 2 ) 、 . . . 、 x ( m ) ,每个数据为 n 维向量 m个数据,n个特征,m个数据分别记为x^{(1)}、x^{(2)}、...、x^{(m)},每个数据为n维向量 m个数据,n个特征,m个数据分别记为x(1)x(2)...x(m),每个数据为n维向量

目标 : 将数据分为 K 部分 , 划分结果保存在 m × 1 列向量 c 中 目标:将数据分为K部分,划分结果保存在m\times1列向量c中 目标:将数据分为K部分,划分结果保存在m×1列向量c

S t e p 1 : 随机初始化 K 个簇心 μ 1 、 μ 2 、 . . . 、 μ K Step1:随机初始化K个簇心\mu_1、\mu_2、...、\mu_K Step1:随机初始化K个簇心μ1μ2...μK

S t e p 2 : 重复 c ( i ) = arg min ⁡ k ∣ ∣ x ( i ) − μ k ∣ ∣ Step2:重复 \quad c^{(i)}=\argmin_{k}||x^{(i)}-\mu{_k}|| Step2:重复c(i)=argmink∣∣x(i)μk∣∣

S t e p 3 : μ k = a v e r a g e ( x ( i ) ) ∣ c ( i ) = k Step3: \mu_k=average(x^{(i)})|c^{(i)}=k Step3:μk=average(x(i))c(i)=k

S t e p 4 : 重复 S t e p 2 和 S t e p 3 Step4:重复Step2和Step3 Step4:重复Step2Step3

注意:在训练过程中,可能出现某一簇(或多)内无点的情况,结果产生K-1(>1)簇。此时可以更改决策方案,或者如果希望目标结果必须产生K个簇,那么可以更改起始簇心位置再次进行聚类。

算法优化

成本函数

既然初始簇心选择不同会导致聚类结果不同,那么如何评估聚类效果并选择最优方案。设计优化函数,首先需要先定义成本函数:
J ( c ( 1 ) , . . . , c ( m ) , μ 1 、 . . . 、 μ K ) = 1 m ∑ i = 1 m ∣ ∣ x ( i ) − μ c ( i ) ∣ ∣ 2 J(c^{(1)},...,c^{(m)},\mu_{1}、...、\mu_{K})=\frac{1}{m}\sum_{i=1}^{m}||x^{(i)}-\mu_{c^{(i)}}||^2 J(c(1),...,c(m),μ1...μK)=m1i=1m∣∣x(i)μc(i)2

由于聚类结果的具体表现是各个簇心的位置以及每个数据被归类情况,因此J包含了上面所示的m+K个参数。这里的成本函数是平均每个数据点到所处簇心距离的平方。再回过头看上面的算法步骤,我们发现算法实际上就是不断减少J的过程:

Step 2 : fix μ \mu μ,assign c c c to minimize J(固定簇心位置,分配每个数据点给最近的簇心,下降J)

Step 3 : fix c,shift μ \mu μ to minimize J(固定每个数据点所属簇,中心化簇心位置,下降J)

In theory : J keep going down and converge(理论上,J不断下降直至收敛)

有了成本函数,我们就可以采用蒙特卡罗思想,进行多次试验,不同初始化得到的最终结果存在差异,挑选cost最小的作为最优方案。

初始化方法

还有一个问题需要解决,如何随机初始化簇心?下面是几种随机初始化方法:

随机选择数据点
方法:从数据集中随机选择 K 个数据点作为初始簇心。
优点:简单易行,快速实现。
缺点:可能会选择到极端点,导致不良结果。

分布式初始化
方法:将数据空间划分为 K 个区域,然后从每个区域中随机选择一个数据点作为簇心。
优点:可以确保簇心的初始位置分散,避免集中在某一部分数据上。

K-means++
方法:在选择每个新的簇心时,使得新簇心与已有簇心的距离尽可能远。具体步骤如下:
随机选择一个数据点作为第一个簇心。
对于每个数据点,计算其与已选择簇心的最小距离。
根据这些距离的平方(即 D(x)^2)进行概率选择,选择下一个簇心。
重复步骤 2 和 3 直到选择到 K 个簇心。
优点:能显著提高聚类效果,通常收敛速度更快,得到的结果更稳定。

注: 关于概率选择,可以使用numpy.random中的choice函数,示例:

next_center = np.random.choice(X, p=probabilities)

K的选择

有时候我们并不能提前根据数据点的分布确定聚类的类别数量K,或者对K的选择没有什么思路,以下是关于K的一些选择策略和解释:

肘部法 elbow method :
方法:通过绘制K-J曲线,选择合适的K(下降变化速率发生突变的临界K值)
弊端:不适用于平滑下降的曲线
在这里插入图片描述

除了上面的技术方法,考虑实际业务需求和可解释性也非常重要。例如:

  • 市场需求:根据市场调研和客户反馈,了解消费者对不同型号的需求。这可以帮助你决定是否需要更多的细分(即更多的聚类)或者更简单的分类(即更少的聚类)。
  • 生产和库存管理:更多的型号意味着更复杂的生产和库存管理。评估你的生产能力和库存管理能力,确定是否能有效管理更多的型号。
  • 可解释性:更多的聚类可能导致更难解释每个型号的特点,特别是对销售和市场团队而言。确保每个聚类(型号)都能被清晰地描述和定位。

代码实现

K-means算法每个步骤函数以及最后整合的完整如下,

import numpy as np
import matplotlib.pyplot as plt


# 计算每个数据点所归属的簇
def find_closest_centroids(X, centroids):
    K = centroids.shape[0]
    m = X.shape[0]
    idx = np.zeros(m, dtype=int)
    for i in range(m):
        idx[i] = np.argmin(np.sum((X[i] - centroids) ** 2, axis=1))
    return idx


# 根据当前分类情况计算新的簇心
def compute_centroids(X, idx, K):
    m, n = X.shape
    centroids = np.zeros((K, n))
    for k in range(K):
        cond = (idx == k)
        if cond.any():
            X_k = X[cond]
            centroids[k] = np.mean(X_k, axis=0)
        else:  # 如果没有点被分配到这个簇,则随机选择一个点作为新的簇心
            centroids[k] = X[np.random.choice(X.shape[0])]
    return centroids


# 随机初始化簇心
def kMeans_init_centroids(X, K):
    randidx = np.random.permutation(X.shape[0])
    centroids = X[randidx[:K]]
    return centroids


# 成本函数
def KMeans_compute_cost(X, centroids, idx):
    m = X.shape[0]
    cost = 0
    for i in range(m):
        K_idx = idx[i]
        X_centroid = centroids[K_idx]
        cost += np.sum((X_centroid - X[i]) ** 2)
    return cost / m


# 运行 K-means 聚类算法
def run_kMeans(X, K, max_iters=10, test_times=50):
    m, n = X.shape
    min_cost = float('inf')
    best_idx = np.zeros(m)
    best_centroids = np.zeros((K, n))

    for j in range(test_times):
        print(f'K-Means test {j}/{test_times - 1}:')
        initial_centroids = kMeans_init_centroids(X, K)
        centroids = initial_centroids

        for i in range(max_iters):
            print(f'K-Means iteration {i}/{max_iters - 1}', end=', ')
            idx = find_closest_centroids(X, centroids)
            centroids = compute_centroids(X, idx, K)
            cost = KMeans_compute_cost(X, centroids, idx)

        if cost < min_cost:
            min_cost = cost
            best_idx = idx
            best_centroids = centroids
            print(f'cost: {cost}, min_cost: {min_cost}')

    return best_centroids, best_idx

为了验证代码正确性和性能,随机在平面内三个点附近生成一系列点,构成试验数据集,并运行聚类算法最后可视化

# 生成数据集
def generate_data():
    np.random.seed(42)
    cluster1 = np.random.randn(100, 2) + np.array([1, 1])
    cluster2 = np.random.randn(100, 2) + np.array([5, 5])
    cluster3 = np.random.randn(100, 2) + np.array([9, 1])
    return np.vstack((cluster1, cluster2, cluster3))


# 可视化数据和聚类结果
def visualize(X, centroids, idx):
    plt.figure(figsize=(8, 6))
    K = centroids.shape[0]

    # 绘制数据点
    for k in range(K):
        plt.scatter(X[idx == k, 0], X[idx == k, 1], label=f'Cluster {k + 1}')

    # 绘制簇心
    plt.scatter(centroids[:, 0], centroids[:, 1], s=300, c='red', marker='X', label='Centroids')
    plt.title('K-means Clustering')
    plt.xlabel('Feature 1')
    plt.ylabel('Feature 2')
    plt.legend()
    plt.show()


# 主函数
if __name__ == "__main__":
    # 生成数据集
    X = generate_data()

    # 设置簇的数量
    K = 3
    max_iters = 10
    test_times = 50

    # 运行 K-means 聚类
    best_centroids, best_idx = run_kMeans(X, K, max_iters, test_times)

    # 可视化结果
    visualize(X, best_centroids, best_idx)

实验结果:可以看到聚类效果很好,三个簇心几乎与数据集构建的三个起始点重合。
在这里插入图片描述

4.案例实战:图像压缩

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

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

相关文章

Unity教程(十六)敌人攻击状态的实现

Unity开发2D类银河恶魔城游戏学习笔记 Unity教程&#xff08;零&#xff09;Unity和VS的使用相关内容 Unity教程&#xff08;一&#xff09;开始学习状态机 Unity教程&#xff08;二&#xff09;角色移动的实现 Unity教程&#xff08;三&#xff09;角色跳跃的实现 Unity教程&…

C++STL的Stack的使用:STL栈和队列的使用介绍、leecode---最小栈、nowcoder---栈的压入、弹出序列等的介绍

文章目录 前言一、STL栈和队列的使用二、leetcode---最小栈三、nowcoder---栈的压入、弹出序列总结 前言 CSTL的Stack的使用&#xff1a;STL栈和队列的使用介绍、leecode—最小栈、nowcoder—栈的压入、弹出序列等的介绍 一、STL栈和队列的使用 #include <iostream> #in…

PCL KD树的使用

目录 一、概述 1.1原理 1.1.1 数据拆分过程 1.1.2 树的构建示例 1.2实现步骤 1.3应用场景 二、代码实现 2.1关键函数 2.1.1KD树构建与查询&#xff1a; 2.1.2 k近邻搜索 2.1.3半径搜索 2.2完整代码 三、实现效果 3.1处理后点云 3.2数据显示 PCL点云算法汇总及实战…

Jboss Administration Console弱⼝令

漏洞描述 Administration Console管理⻚⾯存在弱⼝令&#xff0c;admin:admin&#xff0c;登陆后台上传war包 , getshell 影响版本 全版本 环境搭建 因为这⾥⽤的环境是CVE-2017-12149的靶机 cd vulhub-master/jboss/CVE-2017-12149 docker-compose up -d 密码⽂件 /j…

【SA8155P】AIS Camera相关内容的简单介绍

高通车载相机模块(AIS,Automotive lmage System)是专门针对车载系统特性而设计的一套车载视觉架构,可用于AVM、RVC、DMS等常见车载视频应用开发。车载Camera系统的图像大部分是给自动驾驶等使用,更多考虑的是远距离传输、多摄像头图像处理等场景。 本文仅对AIS Camera相关…

MySQL的登陆错误:ERROR 1049 (42000): Unknown database ‘root‘

MySQL的登陆错误&#xff1a;ERROR 1049 (42000): Unknown database ‘root’ 安装MySQL的时候&#xff0c;到网上查的命令行登陆MySQL的方法都是mysql -u root -p password mysql -r root -p 123456但是奇怪的是这条命令我输进去死活都不对&#xff0c;它都会要求再输入一遍…

21、Tomato

难度 低(个人认为中) 目标 root权限 一个flag 使用VMware启动 kali 192.168.152.56 靶机 192.168.152.66 信息收集 端口信息收集 可以看到有个ftp服务&#xff0c;2211实际是ssh协议端口&#xff0c;80、8888是一个web服务 web测试 80端口显示一个tomato 查看源码给了一些…

从0开始学ARM

1. ARM模式和寄存器 1.1 ARM处理器工作模式 Cortex系列之前的ARM处理器工作模式一共有7种。 1.1.1 工作模式 Cortex系列的ARM处理器工作模式有8种&#xff0c;多了1个monitor模式&#xff0c;如下图所示&#xff1a; ARM之所以设计出这么多种模式出来&#xff0c;就是为了…

三菱变频器RS-485 端子的接线和构成

RS-485 端子排列 RS-485 端子接线方法 RS-485 的计算机1台、变频器1台时 RS-485 的计算机1台、变频器n台(多台)时 通讯运行的初始设定 1、为使变频器和计算机进行 RS-485 通讯&#xff0c;进行必要的设定。 2、通讯分为使用变频器的PU接口的通讯和使用RS-485端子的通讯。 3、…

搜索引擎onesearch3实现解释和升级到Elasticsearch v8系列(四)-搜索

搜索 搜索内容比较多&#xff0c;onesearch分成两部分&#xff0c;第一部分&#xff0c;Query构建&#xff0c;其中包括搜索词设置&#xff0c;设置返回字段&#xff0c;filter&#xff0c;高亮&#xff1b;第二部分分页和排序。第一部分是映射引擎负责&#xff0c;映射通用表…

SAP B1 流程实操 - 营销单据销售部分(下)

背景 在 SAP B1 中&#xff0c;最重要的模块就是【销售】&#xff0c;企业可能不涉及生产和库存&#xff08;贸易公司&#xff09;&#xff0c;甚至不涉及采购&#xff08;服务业&#xff09;&#xff0c;但是一定会有基本的 销售。本文中我们讲解 销售 模块的基本核心&#x…

2024年最新苹果cms升级插件【泛目录专用】

苹果CMS是一款专为视频内容管理而设计的系统&#xff0c;近年来在视频站点搭建中逐渐成为热门选择。其直观的用户界面和灵活的管理功能&#xff0c;使得无论是新手还是专业开发者都能轻松上手。 苹果CMS提供了多种主题和模板&#xff0c;用户可以根据自身需求进行定制&#xf…

Python画笔案例-054 绘制流光溢彩动画

1、绘制流光溢彩动画 通过 python 的turtle 库绘制 流光溢彩动画&#xff0c;如下图&#xff1a; 2、实现代码 绘制流光溢彩动画&#xff0c;以下为实现代码&#xff1a; """本程序实现流光溢彩的动画效果 """ from turtle import * from color…

from tqdm.auto import tqdm用法详细介绍

tqdm 是一个 Python 库&#xff0c;用于在长时间运行的任务中显示进度条。tqdm.auto 是 tqdm 的一个版本&#xff0c;能够自动适配输出环境&#xff08;如 Jupyter Notebook、命令行等&#xff09;&#xff0c;以确保进度条在各种环境下显示正确。下面是 tqdm.auto 的详细用法介…

【刷题】杨辉三角

目录 杨辉三角题目描述解题思路解题代码 相同的树题目描述解题思路 二叉树的层序遍历题目描述解题思路解题代码从底层层序遍历 二叉树的最近公共祖先题目描述解题思路 从前序与中序遍历序列构建二叉树题目描述解题思路 从后序与中序遍历序列构建二叉树题目描述解题思路 根据二叉…

SAP-MM-变式的设置

1、报表变式 业务需求: 业务人员查询报表时有些值是需要经常输入的,能不能设置成默认值?能不能设置成每次进入报表不选择变式直接是默认值? 解决措施: 1、事物码:MB51 以MB51物料凭证查询为例,其他报表自行举一反三 2、设置变式 首先进入MB51入下图 上图是没有选…

任天堂发言人:不会透露起诉《幻兽帕鲁》开发商细节

任天堂在昨天突然宣布将起诉《幻兽帕鲁》开发商 Pocketpair&#xff0c;除了引起许多玩家不满外&#xff0c;更多的是所有人的疑惑&#xff1a;因为实际上大家内心里觉得任天堂出手是理所当然的&#xff0c;但是为什么是在游戏发布数月后才选择起诉&#xff1f;此次诉讼是“专利…

吴恩达深度学习笔记:卷积神经网络(Foundations of Convolutional Neural Networks)2.1-2.2

目录 第四门课 卷积神经网络&#xff08;Convolutional Neural Networks&#xff09;第二周 深度卷积网络&#xff1a;实例探究&#xff08;Deep convolutional models: case studies&#xff09;2.1 为什么要进行实例探究&#xff1f;&#xff08;Why look at case studies?&…

Python编码系列—Python外观模式:简化复杂系统的快捷方式

&#x1f31f;&#x1f31f; 欢迎来到我的技术小筑&#xff0c;一个专为技术探索者打造的交流空间。在这里&#xff0c;我们不仅分享代码的智慧&#xff0c;还探讨技术的深度与广度。无论您是资深开发者还是技术新手&#xff0c;这里都有一片属于您的天空。让我们在知识的海洋中…

生信初学者教程(八):数据收集

文章目录 数据分布表达谱数据最终数据分布自动下载GSE14520下载GSE149614下载其它数据在确定研究疾病为肝细胞癌**(Liver Hepatocellular Carcinoma: HCC)**后,系统地进行了文献回顾,专注于搜索与HCC相关的荟萃分析文章,以获取该领域的研究动态和已有成果。为了支持的研究…