Bootstrap

机器学习(05)

目录

1. 聚类

1.1 无监督学习

1.1.1 监督学习 vs 无监督学习

1.1.2 聚类(Clustering)核心思想与流程详解

①聚类的核心目标

②关键概念与组件

(1) 相似度度量

(2) 簇中心(Centroid)

③聚类算法分类

④聚类流程(以K均值为例)

⑤实际应用示例

(1)场景:客户细分(市场分割)

(2)可视化代码(Python)

⑥常见挑战与解决方案

⑦总结

1.2 K-均值算法(K-Means Clustering)详解

1.2.1 算法目标

1.2.2 K-均值算法步骤详解

①输入与输出

②迭代步骤详解

(1) 初始化聚类中心

(2) 分配样本到最近中心

(3) 更新聚类中心

(4) 终止条件

③ 完整流程示例

④数学本质与收敛性

⑤代码实现(Python)

1.2.3 关键细节与挑战

① 初始化敏感性与局部最优

②选择簇数 K

③ 特征标准化

1.2.4 优缺点总结

1.2.5 K-means++

①为什么需要 K-means++?

②K-means++ 初始化步骤

③示例说明

④K-means++ vs 随机初始化

⑤代码实现(Python)

⑥ 数学证明与优势

⑦适用场景

1.3 K-均值代价函数与优化过程详解

1.3.1 代价函数(畸变函数)的定义

1.3.2 优化目标

1.3.3 迭代优化过程

①分配步骤(固定簇中心,优化分配)

②更新步骤(固定分配,优化簇中心)

1.3.4 代价函数的单调递减性

1.3.5 示例验证

1.3.6 常见错误与验证

1.3.7 数学证明

1.3.8 代码验证(Python)

1.4 K-均值算法的随机初始化与局部最优问题

1.4.1 随机初始化步骤

1.4.2 局部最小值问题

①问题描述

②原因分析

③示例说明

1.4.3 解决方案:多次随机初始化

①操作步骤

② 代码示例(Python)

③ 适用性与局限性

1.4.4 改进方法:K-means++ 初始化

①核心思想

② 步骤

③代码实现

1.4.5 最佳实践总结

1.4.6 总结

1.5 聚类数选择方法详解

1.5.1 肘部法则(Elbow Method)

1.5.2 轮廓系数(Silhouette Coefficient)

1.5.3 外部评估指标(需真实标签)

① 均一性(Homogeneity)与完整性(Completeness)

② V-measure

③调整兰德指数(Adjusted Rand Index, ARI)

1.5.4 相似度/距离计算方法

1.5.5 实际应用示例

1.5.6 代码实现(Python)

① 肘部法则与轮廓系数

② 外部评估指标(V-measure 和 ARI)

1.5.7 总结


1. 聚类

1.1 无监督学习

1.1.1 监督学习 vs 无监督学习

特性监督学习无监督学习
数据标签训练数据包含输入 X 和输出 y(标签)。数据仅包含输入 X,无标签。
目标学习从 X 到 y 的映射关系(分类或回归)。发现数据中的隐藏结构(如聚类、降维、关联规则)。
典型算法线性回归、逻辑回归、支持向量机、神经网络。K均值聚类、层次聚类、主成分分析(PCA)、关联规则挖掘(如Apriori)。

1.1.2 聚类(Clustering)核心思想与流程详解

①聚类的核心目标

将数据划分为若干组(簇),使得:

  • 簇内相似度最大化:同一簇的样本在特征空间中紧密聚集。
  • 簇间相似度最小化:不同簇的样本在特征空间中明显分离。

②关键概念与组件
(1) 相似度度量
  • 欧氏距离(Euclidean Distance)d(x, y) = \sqrt{\sum_{i=1}^n (x_i - y_i)^2}

    • 适用场景:连续数值型数据,特征空间为欧氏空间(如物理测量数据)。
    • 特点:对特征尺度敏感,需标准化处理。
  • 余弦相似度(Cosine Similarity)\text{similarity}(x, y) = \frac{x \cdot y}{\|x\| \cdot \|y\|}

    • 适用场景:文本数据、高维稀疏数据(如TF-IDF向量)。
    • 特点:忽略向量长度,关注方向一致性。
  • 曼哈顿距离(Manhattan Distance)d(x, y) = \sum_{i=1}^n |x_i - y_i|

    • 适用场景:网格状路径数据(如城市街区距离)。
(2) 簇中心(Centroid)
  • 定义:簇内所有样本的均值点,代表簇的“中心位置”。
  • 更新规则(以K均值算法为例):\mu_k = \frac{1}{|C_k|} \sum_{x \in C_k} x
    • 示例:若簇包含样本 (1,2), (3,4), (5,6),则簇中心为 (3,4)。

③聚类算法分类
算法类型代表算法核心思想适用场景
划分式聚类K均值(K-Means)通过迭代优化簇中心,最小化样本到中心的距离平方和。球形簇、大规模数据
层次聚类AGNES、DIANA通过合并或分裂构建树状聚类结构(凝聚式或分裂式)。小规模数据、需层次关系分析
密度聚类DBSCAN基于样本密度划分簇,可发现任意形状簇并识别噪声点。非球形簇、含噪声数据
模型聚类高斯混合模型(GMM)假设数据由多个高斯分布生成,通过EM算法估计参数。概率软聚类、重叠簇

④聚类流程(以K均值为例)
  • 数据预处理

    • 标准化(Z-Score)或归一化(Min-Max)以消除尺度差异。
    • 处理缺失值或异常值。
  • 选择聚类数 K

    • 肘部法则:绘制不同 K 值的畸变函数(Distortion),选择拐点。
    • 轮廓系数:综合衡量簇内紧密度和簇间分离度,值越接近1越好。
  • 初始化簇中心

    • 随机选择 K 个样本作为初始中心(或使用K-means++优化初始化)。
  • 迭代优化

    • 分配样本:将每个样本分配到最近的簇中心。
    • 更新中心:重新计算簇内样本均值作为新中心。
    • 终止条件:中心不再变化或达到最大迭代次数。
  • 结果评估与可视化

    • 使用降维技术(如PCA、t-SNE)将高维数据投影到2D/3D空间。
    • 绘制簇分布图,直观验证聚类效果。

⑤实际应用示例
(1)场景:客户细分(市场分割)
  • 数据:客户购买记录(如消费频率、金额、产品类别)。
  • 步骤
    • 标准化数据,消除量纲差异。
    • 使用K均值聚类将客户分为 K=5个群体。
    • 分析每类客户的消费特征:
      • 簇1:高频高额客户(VIP)。
      • 簇2:低频低额客户(潜在流失客户)。
    • 制定针对性营销策略。
(2)可视化代码(Python)
import matplotlib.pyplot as plt
from sklearn.cluster import KMeans
from sklearn.datasets import make_blobs

# 生成模拟数据
X, _ = make_blobs(n_samples=300, centers=4, cluster_std=0.6, random_state=42)

# K均值聚类
kmeans = KMeans(n_clusters=4, init='k-means++', max_iter=300)
kmeans.fit(X)
labels = kmeans.labels_
centers = kmeans.cluster_centers_

# 绘制结果
plt.scatter(X[:, 0], X[:, 1], c=labels, cmap='viridis', edgecolor='k')
plt.scatter(centers[:, 0], centers[:, 1], c='red', s=200, marker='X', label='簇中心')
plt.title("K均值聚类结果")
plt.xlabel("特征1")
plt.ylabel("特征2")
plt.legend()
plt.show()

⑥常见挑战与解决方案
挑战解决方案
初始中心敏感使用K-means++初始化,或多次运行取最优结果。
非球形簇改用DBSCAN或谱聚类。
噪声数据干扰使用DBSCAN自动识别噪声,或设置异常值过滤阈值。
高维数据稀疏性先降维(如PCA)后聚类,或使用余弦相似度。

⑦总结
  • 核心目标:通过无监督学习发现数据内在结构,无需依赖标签。
  • 关键步骤:选择相似度度量 → 确定聚类数 → 初始化与迭代优化 → 结果验证。
  • 算法选择:根据数据形状(球形/非球形)、规模、噪声情况灵活选用算法。
  • 实践要点:数据预处理(标准化)和结果评估(轮廓系数)不可忽视。

通过合理应用聚类算法,可有效解决客户分群、图像分割、社交网络分析等实际问题,为后续决策提供数据支持。


1.2 K-均值算法(K-Means Clustering)详解

1.2.1 算法目标

将数据集中的样本划分为 K 个簇(组),使得:

  • 同一簇内的样本相似度高(簇内距离小)。
  • 不同簇间的样本相似度低(簇间距离大)。

1.2.2 K-均值算法步骤详解

①输入与输出
  • 输入
    • 数据集 X = \{x^{(1)}, x^{(2)}, ..., x^{(m)}\},其中每个样本 x^{(i)} \in \mathbb{R}^n(n维特征)。
    • 预设簇数 K(需提前指定)。
  • 输出
    • K 个簇的中心点 \mu_1, \mu_2, ..., \mu_K
    • 每个样本的簇标签 c^{(1)}, c^{(2)}, ..., c^{(m)},其中 c^{(i)} \in \{1, 2, ..., K\}

②迭代步骤详解
(1) 初始化聚类中心

操作:随机选择 K 个样本作为初始簇中心 \mu_1, \mu_2, ..., \mu_K​。

示例:假设数据集有 5 个样本,选择 K=2

  • 初始中心可能是 \mu_1 = x^{(2)}, \quad \mu_2 = x^{(4)}

注意

  • K-means++:改进的初始化方法,使初始中心尽可能分散,减少局部最优风险。
  • 避免空簇:若某簇无样本,需重新选择中心或直接删除该簇。
(2) 分配样本到最近中心

公式c^{(i)} = \arg\min_{k} \|x^{(i)} - \mu_k\|^2

操作:对每个样本 x^{(i)},计算其到所有簇中心的欧氏距离平方,选择最近的簇中心索引 k 作为其标签 c^{(i)}

计算示例

  • 样本 x^{(i)} = [3, 5],簇中心 \mu_1 = [1, 2]\mu_2 = [4, 6]
  • 距离平方:

\|x^{(i)} - \mu_1\|^2 = (3-1)^2 + (5-2)^2 = 4 + 9 = 13|x^{(i)} - \mu_2\|^2 = (3-4)^2 + (5-6)^2 = 1 + 1 = 2

  • 因此 c^{(i)} = 2,分配到第二个簇。

关键点

  • 使用欧氏距离平方而非实际距离,避免计算平方根,提升效率。
  • 若特征尺度差异大,需先标准化(如 Z-Score)。
(3) 更新聚类中心

公式\mu_k = \frac{1}{|C_k|} \sum_{x^{(i)} \in C_k} x^{(i)}

操作:对每个簇 k,计算其所有样本的均值作为新中心。

计算示例

  • 簇 k=2 包含样本 [3,5]、[4,6]、[5,7]。
  • 新中心:\mu_2 = \left( \frac{3+4+5}{3}, \frac{5+6+7}{3} \right) = (4, 6)

关键点

  • 若簇为空(无样本),需重新初始化该簇中心或直接忽略。
  • 均值计算是簇内样本的几何中心,确保簇内紧密性。
(4) 终止条件
  • 中心不再变化:所有簇中心两次迭代间的变化小于阈值(如 \|\mu_k^{\text{new}} - \mu_k^{\text{old}}\| < \epsilon)。
  • 达到最大迭代次数:预设一个最大迭代次数(如 300),防止无限循环。

③ 完整流程示例

数据集:二维空间中的 6 个样本(如图)。
目标:分为 2 个簇(K=2)。

样本特征1特征2
x^{(1)}11
x^{(2)}12
x^{(3)}21
x^{(4)}54
x^{(5)}65
x^{(6)}75

步骤演示

  • 初始化:随机选择 \mu_1 = x^{(1)} = (1,1)\mu_2 = x^{(4)} = (5,4)
  • 第一次分配
    • x^{(1)}, x^{(2)}, x^{(3)} 分配到簇1(距离 \mu_1​ 更近)。
    • x^{(4)}, x^{(5)}, x^{(6)} 分配到簇2。
  • 第一次更新中心
    • \mu_1 = \left( \frac{1+1+2}{3}, \frac{1+2+1}{3} \right) = (1.33, 1.33)
    • \mu_2 = \left( \frac{5+6+7}{3}, \frac{4+5+5}{3} \right) = (6, 4.67)
  • 第二次分配
    • x^{(1)}, x^{(2)}, x^{(3)} 仍属于簇1。
    • x^{(4)}可能被重新分配到簇1(需重新计算距离)。
  • 迭代直至收敛:中心不再变化。

④数学本质与收敛性
  • 代价函数:畸变函数 J = \sum_{i=1}^m \|x^{(i)} - \mu_{c^{(i)}}\|^2
  • 收敛性:每次迭代 J 单调递减,最终收敛到局部最优(不一定是全局最优)。

⑤代码实现(Python)
import numpy as np

def k_means(X, K, max_iters=100, tol=1e-4):
    # 随机初始化中心
    centroids = X[np.random.choice(X.shape[0], K, replace=False)]
    
    for _ in range(max_iters):
        # 分配样本到最近中心
        distances = np.sqrt(((X - centroids[:, np.newaxis])**2).sum(axis=2))
        labels = np.argmin(distances, axis=0)
        
        # 更新中心
        new_centroids = np.array([X[labels == k].mean(axis=0) for k in range(K)])
        
        # 检查收敛
        if np.all(np.abs(new_centroids - centroids) < tol):
            break
        centroids = new_centroids
    
    return centroids, labels

# 示例数据
X = np.array([[1,1], [1,2], [2,1], [5,4], [6,5], [7,5]])
centroids, labels = k_means(X, K=2)
print("簇中心:\n", centroids)
print("样本标签:", labels)

1.2.3 关键细节与挑战

① 初始化敏感性与局部最优
  • 问题:随机初始中心可能导致算法收敛到局部最优解。
  • 解决方案
    • K-means++:优化初始化,使初始中心点尽可能远离彼此。
    • 多次运行:随机初始化多次,选择畸变函数最小的结果。
②选择簇数 K
  • 肘部法则(Elbow Method)

    • 绘制不同 K 值对应的畸变函数值 J,选择拐点处的 K。
  • 轮廓系数(Silhouette Score)

s(i) = \frac{b(i) - a(i)}{\max(a(i), b(i))}

  • a(i):样本 i 到同簇其他样本的平均距离。
  • b(i):样本 i 到最近其他簇样本的平均距离。
  • 值越接近1,聚类效果越好。
③ 特征标准化
  • 必要性:若特征尺度差异大(如身高[1.5m, 2.0m] vs 体重[50kg, 100kg]),需标准化(如Z-Score)。
  • 方法x_{\text{scaled}} = \frac{x - \mu}{\sigma}

1.2.4 优缺点总结

优点缺点
简单高效,时间复杂度 O(mKt)需预先指定 K,且对初始中心敏感。
结果直观,适合球形簇。无法处理非球形簇(如环形分布)。
可扩展性强,适合大规模数据。对噪声和异常值敏感。

1.2.5 K-means++

①为什么需要 K-means++?

传统的 K-means 算法随机选择初始簇中心,可能导致以下问题:

  • 局部最优陷阱:初始中心集中在同一区域,导致算法收敛到次优解。
  • 空簇问题:某些簇可能因初始中心过近而无法分配到样本。
  • 收敛速度慢:需要更多迭代次数才能稳定。

K-means++ 通过改进初始化策略,使初始中心尽可能分散,从而提升聚类效果和稳定性。


②K-means++ 初始化步骤

输入:数据集 X = \{x^{(1)}, x^{(2)}, ..., x^{(m)}\},簇数 K。
输出:初始簇中心 \mu_1, \mu_2, ..., \mu_K​。

步骤

  • 随机选择第一个中心\mu_1 \leftarrow \text{Randomly select a sample from } X

  • 选择后续中心(k = 2 到 K):

    • 对每个样本 x^{(i)},计算其到最近已选中心的距离平方 D(x^{(i)})^2
    • 计算每个样本被选为下一个中心的概率:P(x^{(i)}) = \frac{D(x^{(i)})^2}{\sum_{j=1}^m D(x^{(j)})^2}
    • 按概率分布 P(x^{(i)}) 随机选择一个样本作为新中心 \mu_k​。
  • 重复步骤2,直到选出 K 个初始中心。


③示例说明

数据集:二维空间中的样本点。
目标:选择 K=3 个初始中心。

  1. 随机选择第一个中心:假设选中 \mu_1 = A
  2. 计算距离与概率
    • 样本 B 到 \mu_1​ 的距离平方为 4。
    • 样本 C 到 \mu_1​ 的距离平方为 9。
    • 总距离平方和 4 + 9 + ... = 50。
    • 概率 P(B) = 4/50 = 8%,P(C) = 9/50 = 18%,依此类推。
  3. 按概率选择第二个中心:假设选中距离较远的 \mu_2 = C
  4. 选择第三个中心:计算所有样本到 \mu_1 \text{ and } \mu_2​ 的最近距离,按概率选择 \mu_3 = E

效果:初始中心分散在数据的不同区域,覆盖潜在簇结构。


④K-means++ vs 随机初始化
指标K-means++随机初始化
初始中心分布分散,覆盖不同簇可能聚集,忽略稀疏区域
收敛速度更快(需更少迭代次数)较慢
结果稳定性高(重复运行结果一致)低(不同运行结果可能差异大)
局部最优风险

⑤代码实现(Python)

在 scikit-learn 中,K-means++ 是默认初始化方法:

from sklearn.cluster import KMeans

# 使用 K-means++ 初始化
kmeans = KMeans(
    n_clusters=3,
    init='k-means++',  # 默认即为 'k-means++'
    n_init=10,         # 运行10次取最优结果
    max_iter=300,
    random_state=42
)
kmeans.fit(X)

# 输出初始中心
print("初始中心:\n", kmeans.cluster_centers_)

⑥ 数学证明与优势
  • 理论保证:K-means++ 的期望畸变函数值 E[J] 接近最优解的 O(\log K) 倍,远优于随机初始化的最坏情况。
  • 实际效果:在大多数数据集上,K-means++ 显著减少收敛所需的迭代次数,并提高聚类质量。

⑦适用场景
  • 任意形状数据:只要簇间存在明显间隔,K-means++ 均可有效初始化。
  • 高维数据:通过概率选择分散中心,避免维度灾难下的随机偏差。
  • 大规模数据:尽管初始化计算量略高,但总体效率仍优于随机方法。

1.3 K-均值代价函数与优化过程详解

1.3.1 代价函数(畸变函数)的定义

K-均值的核心目标是最小化所有数据点与其所属簇中心之间的距离平方和。代价函数(畸变函数)定义为:J(c^{(1)}, \ldots, c^{(m)}, \mu_1, \ldots, \mu_K) = \frac{1}{m} \sum_{i=1}^m \|x^{(i)} - \mu_{c^{(i)}}\|^2

其中:

  • c^{(i)}:数据点 x^{(i)} 所属的簇索引(c^{(i)} \in \{1, 2, \ldots, K\})。
  • \mu_{c^{(i)}}​:第 c^{(i)} 个簇的中心点。
  • \|x^{(i)} - \mu_{c^{(i)}}\|^2:数据点 x^{(i)} 到其簇中心的欧氏距离平方。

K表示 预设的簇(组)的数量,是用户需要提前指定的超参数,k通常作为 索引变量,用于遍历或表示某个具体的簇。


1.3.2 优化目标

通过调整以下两个变量来最小化代价函数 J:

  • 分配变量 c^{(1)}, c^{(2)}, \ldots, c^{(m)}:每个数据点的簇标签。
  • 簇中心\mu_1, \mu_2, \ldots, \mu_K:每个簇的中心点坐标。

1.3.3 迭代优化过程

K-均值通过交替优化分配变量和簇中心来逐步降低代价函数

①分配步骤(固定簇中心,优化分配)
  • 操作:将每个数据点分配到距离最近的簇中心。
  • 数学表示c^{(i)} = \arg\min_{k} \|x^{(i)} - \mu_k\|^2
  • 作用:固定簇中心 \mu_k​,通过调整 c^{(i)} 减少总距离平方和。
②更新步骤(固定分配,优化簇中心)
  • 操作:重新计算每个簇的中心为该簇内所有数据点的均值。
  • 数学表示\mu_k = \frac{1}{|C_k|} \sum_{x^{(i)} \in C_k} x^{(i)}(其中 C_k​ 是第 k 个簇的样本集合)
  • 作用:固定分配 c^{(i)},通过调整 \mu_k​ 减少总距离平方和。

1.3.4 代价函数的单调递减性

  • 分配步骤:由于每个数据点被分配到最近的簇中心,总距离平方和必然减少或保持不变。
  • 更新步骤:均值是使簇内距离平方和最小的点,因此更新簇中心后总距离平方和必然减少或保持不变。
  • 结论:每次迭代后代价函数 J 不会增加。如果出现 J 增大的情况,说明实现中存在错误(如计算错误或未正确更新簇中心)。

1.3.5 示例验证

数据集:3 个样本点 X = \{[1, 2], [3, 4], [5, 6]\},初始簇中心 \mu_1 = [1, 2]\mu_2 = [3, 4]

  1. 第一次分配

    • x^{(1)} 分配到 \mu_1​,x^{(2)} 和 x^{(3)} 分配到 \mu_2
    • 代价函数:J = \frac{1}{3} \left( 0^2 + 0^2 + \| [5,6] - [3,4] \|^2 \right) = \frac{1}{3} (0 + 0 + 8) = \frac{8}{3} \approx 2.67
  2. 第一次更新簇中心

    • \mu_1 = [1, 2](未变),\mu_2 = \frac{[3,4] + [5,6]}{2} = [4, 5]
  3. 第二次分配

    • x^{(1)} 分配到 \mu_1​,x^{(2)} 和 x^{(3)} 分配到 \mu_2​。
    • 代价函数:J = \frac{1}{3} \left( 0^2 + \| [3,4] - [4,5] \|^2 + \| [5,6] - [4,5] \|^2 \right) = \frac{4}{3},代价函数从 2.672.67 降至 1.331.33。

1.3.6 常见错误与验证

  • 问题1:代价函数未减小

    • 原因:簇中心更新错误(如未计算均值)或分配步骤未找到最近中心。
    • 检查:验证簇中心计算代码,确保使用均值而非中位数或其他统计量。
  • 问题2:代价函数震荡

    • 原因:数据未标准化,导致某些特征主导距离计算(如身高范围 [1.5m, 2.0m] vs 体重范围 [50kg, 100kg])。
    • 解决方案:标准化数据(如 Z-Score 或 Min-Max 归一化)。

1.3.7 数学证明

  • 分配步骤:固定 \mu_k,对每个x^{(i)},选择 c^{(i)} = \arg\min_k \|x^{(i)} - \mu_k\|^2,此时 J 达到给定 \mu_k 下的最小值。

  • 更新步骤:固定 c^{(i)},对每个簇 k,选择 \mu_k = \frac{1}{|C_k|} \sum_{x^{(i)} \in C_k} x^{(i)},此时 J 达到给定 c^{(i)} 下的最小值。

  • 结论:交替优化保证 J 单调递减,直至收敛到局部最小值。


1.3.8 代码验证(Python)

import numpy as np

def compute_cost(X, centroids, labels):
    m = X.shape[0]
    cost = 0.0
    for i in range(m):
        centroid = centroids[labels[i]]
        cost += np.sum((X[i] - centroid) ** 2)
    return cost / m

# 示例数据
X = np.array([[1, 2], [3, 4], [5, 6]])
initial_centroids = np.array([[1, 2], [3, 4]])

# 第一次分配和计算代价
labels = np.argmin(np.sum((X[:, np.newaxis] - initial_centroids) ** 2, axis=2), axis=1)
cost1 = compute_cost(X, initial_centroids, labels)
print("第一次迭代代价:", cost1)

# 更新簇中心
new_centroids = np.array([X[labels == k].mean(axis=0) for k in range(2)])

# 第二次分配和计算代价
labels = np.argmin(np.sum((X[:, np.newaxis] - new_centroids) ** 2, axis=2), axis=1)
cost2 = compute_cost(X, new_centroids, labels)
print("第二次迭代代价:", cost2)

# 验证代价是否减小
assert cost2 <= cost1, "代价函数未减小,存在错误!"

1.4 K-均值算法的随机初始化与局部最优问题

1.4.1 随机初始化步骤

在运行 K-均值算法前,需随机初始化聚类中心。具体步骤如下。

  • 确定簇数 K
    • 确保 K < m(簇数小于样本数量),否则可能产生空簇或重复中心。
  • 随机选择初始中心
    • 从训练集中随机选择 K 个不同的样本,将其坐标作为初始聚类中心。
    • 示例:若数据集有 1000 个样本,选择 K=3,则随机抽取 3 个样本作为初始中心 \mu_1, \mu_2, \mu_3​。

1.4.2 局部最小值问题

①问题描述

K-均值的代价函数(畸变函数)可能存在多个局部最小值,算法可能收敛到其中一个次优解而非全局最优解。

②原因分析
  • 初始化敏感:初始中心的位置直接影响最终聚类结果。
  • 非凸优化:代价函数 J 是非凸的,存在多个“山谷”(局部最小值)。
③示例说明

假设数据集有两个自然簇,但随机初始化中心时:

  • 情况1:初始中心分别位于两个簇内 → 收敛到全局最优。
  • 情况2:初始中心均位于同一簇 → 收敛到局部最优(错误分割)。

1.4.3 解决方案:多次随机初始化

①操作步骤
  1. 多次运行算法:例如运行 50 次,每次使用不同的随机初始中心。
  2. 计算每次的代价函数:记录每次聚类结果的畸变函数 J。
  3. 选择最优结果:取 J 最小的聚类结果作为最终解。
② 代码示例(Python)
from sklearn.cluster import KMeans
import numpy as np

# 假设数据集为 X
best_inertia = float('inf')
best_labels = None
best_centers = None

for _ in range(50):  # 运行50次
    kmeans = KMeans(n_clusters=3, init='random', n_init=1)
    kmeans.fit(X)
    if kmeans.inertia_ < best_inertia:
        best_inertia = kmeans.inertia_
        best_labels = kmeans.labels_
        best_centers = kmeans.cluster_centers_

print("最优代价:", best_inertia)
③ 适用性与局限性
  • 适用场景:当 K 较小(如 2-10)时,多次运行能显著提高找到全局最优的概率。
  • 局限性
    • K 较大时,计算成本急剧增加,且效果提升有限。
    • 无法完全避免局部最优,但可降低风险。

1.4.4 改进方法:K-means++ 初始化

①核心思想

通过概率选择初始中心,使中心点尽可能分散,减少局部最优风险。

② 步骤
  • 随机选择第一个中心。
  • 后续中心按距离概率选择(距离越远的点被选中的概率越高)。
③代码实现

在 scikit-learn 中,K-means++ 是默认初始化方法

kmeans = KMeans(n_clusters=3, init='k-means++')  # 使用 K-means++ 初始化
kmeans.fit(X)

1.4.5 最佳实践总结

  • 初始化策略
    • 优先使用 K-means++ 替代纯随机初始化。
    • 若资源允许,结合多次随机初始化(如 10 次)并选择最优结果。
  • 选择 K
    • 使用 肘部法则 或 轮廓系数 确定最佳簇数。
  • 数据预处理
    • 标准化数据(如 Z-Score)以避免特征尺度差异影响距离计算。

1.4.6 总结

  • 随机初始化是 K-均值的基础步骤,但易陷入局部最优。
  • 多次运行可缓解局部最优问题,但计算成本随 K 增大而增加。
  • K-means++ 是更高效的初始化方法,推荐作为默认选择。

通过合理选择初始化策略和验证方法,可以显著提升 K-均值算法的聚类效果和稳定性。


1.5 聚类数选择方法详解

1.5.1 肘部法则(Elbow Method)

核心思想:通过观察不同 K 值对应的畸变函数(Distortion)变化,找到“肘点”作为最佳聚类数。
畸变函数:所有样本到其簇中心的距离平方和的均值:J(K) = \frac{1}{m} \sum_{i=1}^m \|x^{(i)} - \mu_{c^{(i)}}\|^2

操作步骤

  • 对 K=1,2,...,K_{\text{max}} 分别运行 K-均值算法。
  • 计算每个 K 对应的畸变值 J(K)。
  • 绘制 K 与 J(K) 的关系曲线,选择拐点(肘点)对应的 K。

示例:当 K=3 时,畸变值下降速度显著变缓,因此选择 K=3。


1.5.2 轮廓系数(Silhouette Coefficient)

核心思想:综合衡量样本的簇内紧密度和簇间分离度,值越接近1表示聚类效果越好。
公式s(i) = \frac{b(i) - a(i)}{\max(a(i), b(i))}

  • a(i):样本i 到同簇其他样本的平均距离(簇内不相似度)。
  • b(i):样本i到最近其他簇样本的平均距离(簇间不相似度)。

操作步骤

  • 对每个 K 计算所有样本的轮廓系数并取均值。
  • 选择轮廓系数最大的 K。

示例图

  • 横轴:聚类数 K(如 K=2, 3, 4, 5)。
  • 纵轴:平均轮廓系数。
  • 关键点
    • 当 K=3 时,平均轮廓系数达到峰值(约 0.7),表明此时聚类效果最优。
    • K=2 时轮廓系数较低(簇内不够紧密或簇间分离不足)。
    • K>3 时轮廓系数下降,可能因过分割导致簇间差异减小。

1.5.3 外部评估指标(需真实标签)

① 均一性(Homogeneity)与完整性(Completeness)
  • 均一性 p:每个簇中只包含单一类别的样本的比例(类似精确率)。
  • 完整性 r:同类别样本被分配到同一簇的比例(类似召回率)。
② V-measure

均一性和完整性的调和平均:V = \frac{(1+\beta^2) \cdot p \cdot r}{\beta^2 \cdot p + r}

  • \beta:权重参数(默认 \beta=1)。
③调整兰德指数(Adjusted Rand Index, ARI)

衡量聚类结果与真实标签的相似性,值越接近1表示聚类效果越好。

\text{ARI} = \frac{\sum_{i,j} \binom{n_{ij}}{2} - \frac{[\sum \binom{a_i}{2} \sum \binom{b_j}{2}]}{\binom{n}{2}}}{\frac{1}{2} [\sum \binom{a_i}{2} + \sum \binom{b_j}{2}] - \frac{[\sum \binom{a_i}{2} \sum \binom{b_j}{2}]}{\binom{n}{2}}}

  • a_i, b_j:簇 i 和真实类 j 的样本数。
  • n_{ij}​:同时属于簇 i 和真实类 j 的样本数。

1.5.4 相似度/距离计算方法

方法公式适用场景
欧氏距离d(x,y) = \sqrt{\sum_{i=1}^n (x_i - y_i)^2}连续数值数据(如物理测量)
余弦相似度\cos(\theta) = \frac{x^T y}{\|x\| \cdot \|y\|}文本数据、高维稀疏数据
杰卡德相似系数J(A, B) = \frac{|A \cap B|}{|A \cup B|}适用于衡量二元存在性集合的相似性,如用户行为分析(购买记录)、文本关键词对比或生物序列特征匹配
皮尔逊相关系数\rho_{XY} = \frac{\text{cov}(X,Y)}{\sigma_X \sigma_Y}标准化后的连续数据

1.5.5 实际应用示例

场景:T恤尺寸设计

  • 目标:根据用户身材数据(身高、体重)聚类,确定生产尺寸种类(如 S/M/L 或 XS/S/M/L/XL)。
  • 步骤
    • 使用肘部法则或轮廓系数选择最佳 K。
    • 若 K=3,分为 S/M/L;若 K=5,分为 XS/S/M/L/XL。
    • 结合业务需求(如生产成本、用户满意度)最终确定 K。

1.5.6 代码实现(Python)

① 肘部法则与轮廓系数
from sklearn.cluster import KMeans
from sklearn.metrics import silhouette_score
import matplotlib.pyplot as plt

# 生成数据
X, _ = make_blobs(n_samples=500, centers=4, random_state=42)

# 计算不同K的畸变值和轮廓系数
distortions = []
silhouettes = []
K_range = range(2, 10)

for k in K_range:
    kmeans = KMeans(n_clusters=k, random_state=42)
    labels = kmeans.fit_predict(X)
    distortions.append(kmeans.inertia_)
    silhouettes.append(silhouette_score(X, labels))

# 绘制肘部法则
plt.figure(figsize=(12, 4))
plt.subplot(1, 2, 1)
plt.plot(K_range, distortions, 'bx-')
plt.xlabel('K')
plt.ylabel('Distortion')
plt.title('Elbow Method')

# 绘制轮廓系数
plt.subplot(1, 2, 2)
plt.plot(K_range, silhouettes, 'rx-')
plt.xlabel('K')
plt.ylabel('Silhouette Score')
plt.title('Silhouette Analysis')
plt.show()
② 外部评估指标(V-measure 和 ARI)
from sklearn.metrics import v_measure_score, adjusted_rand_score

# 真实标签 y_true 和聚类标签 y_pred
v_score = v_measure_score(y_true, y_pred)
ari = adjusted_rand_score(y_true, y_pred)

print(f"V-measure: {v_score:.3f}")
print(f"ARI: {ari:.3f}")

1.5.7 总结

  • 肘部法则:适合快速找到拐点,但需人工判断。
  • 轮廓系数:量化评估聚类质量,适合自动化选择。
  • 外部指标(V-measure、ARI):需真实标签,用于验证聚类与已知分类的一致性。
  • 业务需求:最终聚类数需结合应用场景(如产品设计、用户分群)。

通过综合使用这些方法,可以科学地选择最佳聚类数,提升模型效果和业务价值。

;