返回列表

K-均值聚类算法详解

发布于 ·

K-均值聚类算法详解

1. 概述

K-均值(K-Means)是最经典和广泛使用的聚类算法之一,由 Stuart Lloyd 于1957年提出。它是一种无监督学习算法,旨在将一组未标记的数据点划分为K个簇(cluster),使得每个数据点都属于离它最近的簇中心(centroid)。K-均值的目标是使簇内误差平方和(Within-Cluster Sum of Squares, WCSS)最小化。

1.1 核心思想

  • 随机选择K个初始质心(centroids)。
  • 将每个数据点分配给最近的质心所在的簇。
  • 重新计算每个簇的质心(即该簇所有点的均值)。
  • 重复上述步骤,直到质心不再变化或达到最大迭代次数。

2. 算法步骤

以下是K-均值算法的详细步骤:

  1. 选择簇的数量K
需要预先指定要划分的簇数K。选择合适的K值是一个挑战,常用方法包括肘部法则(Elbow Method)和轮廓系数(Silhouette Score)。
  1. 初始化质心
随机选择K个数据点作为初始质心。
  1. 分配数据点到簇
对每个数据点,计算其与各质心的欧氏距离,并将其分配到距离最近的质心所属的簇。
  1. 更新质心
重新计算每个簇中所有点的均值,作为新的质心。
  1. 重复步骤3和4
直到质心不再显著变化(收敛)或达到预设的最大迭代次数。

3. 数学公式

设数据集为 $ \{x1, x2, ..., xn\} $,其中 $ xi \in \mathbb{R}^d $。

  • 目标函数(WCSS):
$$ J = \sum{i=1}^{K} \sum{x \in Ci} \|x - \mui\|^2 $$ 其中 $ Ci $ 是第i个簇,$ \mui $ 是该簇的质心。
  • 质心更新公式:
$$ \mui = \frac{1}{|Ci|} \sum{x \in Ci} x $$

4. 代码实现(Python示例)

import numpy as np
import matplotlib.pyplot as plt
from sklearn.datasets import makeblobs
from sklearn.metrics import silhouettescore

生成示例数据

X, _ = makeblobs(nsamples=300, centers=4, clusterstd=1.0, randomstate=42)

K-均值算法实现

class KMeans: def init(self, k=3, maxiters=100): self.k = k self.maxiters = maxiters self.centroids = None

def fit(self, X):
# 随机初始化质心
self.centroids = X[np.random.choice(X.shape[0], self.k, replace=False)]

for in range(self.maxiters):
# 分配簇
labels = self.
assignclusters(X)
# 计算新质心
new
centroids = self.computecentroids(X, labels)
# 检查是否收敛
if np.allclose(self.centroids, newcentroids):
break
self.centroids = new
centroids

return labels

def assignclusters(self, X):
distances = np.linalg.norm(X[:, np.newaxis] - self.centroids, axis=2)
return np.argmin(distances, axis=1)

def computecentroids(self, X, labels):
centroids = np.zeros((self.k, X.shape[1]))
for i in range(self.k):
centroids[i] = X[labels == i].mean(axis=0)
return centroids

使用自定义KMeans

kmeans = KMeans(k=4) labels = kmeans.fit(X)

可视化结果

plt.figure(figsize=(8, 6)) plt.scatter(X[:, 0], X[:, 1], c=labels, cmap='viridis', s=50) plt.scatter(kmeans.centroids[:, 0], kmeans.centroids[:, 1], c='red', marker='x', s=200, linewidths=3) plt.title('K-Means Clustering Result') plt.xlabel('Feature 1') plt.ylabel('Feature 2') plt.show()

评估聚类效果

silscore = silhouettescore(X, labels) print(f"Silhouette Score: {sil_score:.3f}")

5. 优缺点分析

优点

  • 简单易懂,易于实现。
  • 计算效率高,适用于大规模数据集。
  • 在凸形簇且簇大小相近时表现良好。

缺点

  • 需预先指定K值。
  • 对初始质心敏感,可能收敛到局部最优。
  • 对噪声和异常值敏感。
  • 仅适用于球形簇,无法处理非凸形状的簇。

6. 改进与变种

为了克服传统K-均值的局限性,研究者提出了多种改进版本:

| 算法 | 特点 |
|------|------|
| K-Means++ | 优化初始质心选择,提高收敛速度和稳定性 |
| Mini-Batch K-Means | 使用数据子集进行迭代,适合大数据场景 |
| Fuzzy C-Means | 允许一个点属于多个簇(模糊聚类) |
| Gaussian Mixture Models (GMM) | 基于概率模型,可处理复杂形状簇 |


7. 总结

K-均值是一种基础但强大的聚类工具,广泛应用于图像分割、客户分群、文档分类等领域。虽然它存在一些限制,但通过合理选择和调优,仍能有效解决许多实际问题。理解其原理和实现有助于我们更好地应用聚类技术,并为更复杂的无监督学习任务打下基础。

提示:在实际应用中,建议结合肘部法则、轮廓系数等方法确定最佳K值,并通过多次运行取最优结果以减少随机性影响。