sklearn函数总结十二 —— 聚类分析算法K-Means

纯手打,代码整理中,持续更新中^-^

序号延用总结十一

19.K-Means

聚类分析算法是一类强大的无监督学习工具,其核心思想是"物以类聚",通过度量数据点之间的相似性,自动地将数据划分成不同的组(簇),从而帮助我们发现数据中内在的、未知的有价值结构。 scikit-learn(sklearn)中提供了多种常用的聚类算法,如K-Means(K均值),DBSCAN(基于密度的 噪声应用空间聚类),Agglomerative Clustering(凝聚层次聚类)

K-Means(K均值)聚类算法是一种常见的无监督学习算法,广泛用于数据挖掘和模式识别领域。其主要目标是将数据集分为多个簇(cluster),使得同一簇中的数据点相似度较高,而不同簇之间的数据点 相似度较低。

19.1 K-Means 聚类的基本原理

  1. 初始:随机选择K个数据点作为初始质心(centroid),其中K为预先设定的簇的数量。

  2. 分配步骤:对于每个数据点,计算它与K个质心的距离,并将其分配到离它最近的质心所在的簇中。

  3. 更新步骤:一旦所有数据点都被分配到簇中,重新计算每个簇的质心,即计算簇内所有点的均值,并将该均值作为新的质心。

  4. 重复:重复执行分配和更新步骤,直到簇的质心不再发生显著变化或达到最大迭代次数为止。

19.2 K-Means 聚类的优缺点

优点:

  • 计算效率高:对于大数据集,K-Means是非常高效的,时间复杂度是 O (nkt ),其中 n 是样本数,k 是簇的个数,t 是迭代次数。

  • 简单易懂:K-Means算法的原理简单,易于实现。

缺点:

  • K值的选择:需要事先指定簇的个数 K ,但 K 的选择并不容易,且过多或过少的簇数会导致聚类效果差。

  • 容易受初始值影响:K-Means对初始质心非常敏感,容易陷入局部最优解。

  • 不能处理非球形簇:K-Means假设每个簇是球形的,因此对于形状不规则的簇,K-Means可能效果不好。

  • 对噪声敏感:对异常值(outliers)比较敏感,可能影响聚类效果。

19.3 代码示例

python 复制代码
import numpy as np
from sklearn.cluster import KMeans
import matplotlib.pyplot as plt

# 生成一些样本数据
X = np.random.rand(100, 2)  # 100个2维数据点
# 创建KMeans模型,设定簇的个数K=3
kmeans = KMeans(n_clusters=3, random_state=0)

# 训练KMeans模型
kmeans.fit(X)

# 获取每个数据点的簇标签
labels = kmeans.labels_

# 获取簇的质心
centroids = kmeans.cluster_centers_
print(centroids)
# 可视化结果
plt.scatter(X[:, 0], X[:, 1], c=labels, cmap='viridis')  # 根据簇标签着色
plt.scatter(centroids[:, 0], centroids[:, 1], marker='*', color='red')  # 绘制质心
plt.show()

运行结果

19.4 API介绍

在使用 Python 的 Scikit-Learn 库时,我们使用KMeans 类来实现K-Means聚类算法:

python 复制代码
from sklearn.cluster import KMeans

model = KMeans(
    n_clusters=8,
    init='k-means++',
    n_init=10,
    max_iter=300,
    random_state=42
)

核心参数

  • n_clusters(最重要的参数):形成的簇数

  • init(初始化方法)初始化质心的策略。这个一般推荐使用 k-means++

  • n_init,算法用不同的质心种子运行的次数。

  • max_iter:单次运行中的最大迭代次数。

  • random_state::随机数种子,一般是42。

19.5 如何选择合适的K值

选择K值是K-Means聚类中的一个关键问题,常用的两种方法是:1,肘部法则(Elbow Method)2, 轮廓系数(Silhouette Score)

19.5.1 肘部法则(Elbow Method)

通过计算不同K值下的聚类误差平方和(SSE,Sum of Squared Errors),绘制出K值与SSE的关系图。 当K值增加时,SSE会逐渐减小,但当K达到某个值时,SSE的下降速率会显著变缓,这个拐点就是理想的K值("肘部")。

python 复制代码
from sklearn.cluster import KMeans
import matplotlib.pyplot as plt

# 设置中文字体支持
plt.rcParams['font.sans-serif'] = ['SimHei']  # 用来正常显示中文标签
plt.rcParams['axes.unicode_minus'] = False   # 用来正常显示负号
sse = []
for k in range(1, 11):
    kmeans = KMeans(n_clusters=k, random_state=0)
    kmeans.fit(X)
    sse.append(kmeans.inertia_)

plt.plot(range(1, 11), sse)
plt.xlabel('K值')
plt.ylabel('SSE值')
plt.title('肘部法则选K值')
plt.show()

运行结果:

kmeans.inertia_ 是 KMeans 聚类算法中的一个属性,它表示聚类结果的 惯性(inertia)。简单来 说,惯性是所有样本点与其所属簇的质心之间的平方距离的总和。惯性值越小,说明聚类结果越紧凑。

19.5.2 轮廓系数(Silhouette Score)

通过计算轮廓系数来评估不同K值的聚类效果,轮廓系数介于-1和1之间,值越大表示聚类效果越好。

python 复制代码
from sklearn.metrics import silhouette_score

# 设置中文字体支持
plt.rcParams['font.sans-serif'] = ['SimHei']  # 用来正常显示中文标签
plt.rcParams['axes.unicode_minus'] = False   # 用来正常显示负号
silhouette_scores = []
for k in range(2, 11):  # 至少需要2个簇
    kmeans = KMeans(n_clusters=k, random_state=0)
    kmeans.fit(X)
    score = silhouette_score(X, kmeans.labels_)
    silhouette_scores.append(score)

plt.plot(range(2, 11), silhouette_scores)
plt.xlabel('K值')
plt.ylabel('轮廓系数')
plt.title('轮廓系数选K值')
plt.show()

输出结果

相关推荐
Swift社区2 小时前
LeetCode 453 - 最小操作次数使数组元素相等
算法·leetcode·职场和发展
hoiii1872 小时前
LR算法辅助的MIMO系统Zero Forcing检测
算法
糖葫芦君2 小时前
Lora模型微调
人工智能·算法
小李小李快乐不已2 小时前
二叉树理论基础
数据结构·c++·算法·leetcode
仰泳的熊猫2 小时前
1149 Dangerous Goods Packaging
数据结构·c++·算法·pat考试
_OP_CHEN2 小时前
【算法基础篇】(三十七)图论基础之多源最短路:Floyd 算法吃透所有点对最短路径!
算法·蓝桥杯·图论·算法竞赛·floyd算法·acm/icpc·多源最短路
Web极客码2 小时前
如何选择最适合的内容管理系统(CMS)?
java·数据库·算法
程序员三明治3 小时前
【动态规划】01背包与完全背包问题详解,LeetCode零钱兑换II秒解,轻松解力扣
算法·leetcode·动态规划·java后端·01背包·完全背包·零钱兑换
自由生长20243 小时前
大数据计算框架-流式计算的Join
算法