PAM聚类算法及其Python代码实现
聚类是一种常见的数据分析技术,它将相似的数据点分组为一个簇,使得簇内的数据点之间相似度高,而簇间的数据点相似度较低。其中,PAM(Partitioning Around Medoids)聚类算法是一种经典的聚类算法,它通过选择代表性的样本点作为簇的中心(即medoids),并通过最小化总距离的方式来划分数据点。
本文将介绍PAM聚类算法的原理,并使用Python实现一个简单的PAM聚类算法示例。
PAM聚类算法原理
PAM聚类算法主要包含以下几个步骤:
- 随机选择k个样本点作为初始的medoids。
- 根据medoids将所有的数据点分配到最近的簇中。
- 对每个簇,选择一个非medoid的数据点,计算替换后的总距离,选择总距离最小的替换。
- 重复步骤2和步骤3,直到medoids的变化小于某个阈值,或达到最大迭代次数。
Python代码实现
import random
import numpy as np
from scipy.spatial.distance import cdist
def pam_clustering(data, k, max_iter=100):
n = data.shape[0] # 样本点数
m = data.shape[1] # 样本维度
# 随机初始化k个medoids
medoids = random.sample(range(n), k)
for _ in range(max_iter):
# 分配样本点到最近的medoids所属的簇
clusters = [[] for _ in range(k)]
for i in range(n):
distances = cdist(data[i].reshape(1, -1), data[medoids])
cluster_index = np.argmin(distances)
clusters[cluster_index].append(i)
# 计算当前簇内的所有样本点之间的距离和
total_distance = 0
for cluster in clusters:
sub_data = data[cluster]
total_distance += np.sum(cdist(sub_data, sub_data))
# 对每个簇,选择一个非medoid的数据点,计算替换后的总距离,选择总距离最小的替换
for i in range(k):
for member in clusters[i]:
if member not in medoids:
new_medoids = medoids.copy()
new_medoids[i] = member
new_distance = 0
for j in range(k):
sub_data = data[clusters[j]]
new_distance += np.sum(cdist(sub_data, sub_data))
if new_distance < total_distance:
medoids = new_medoids
total_distance = new_distance
return medoids, clusters
# 数据准备
data = np.array([[1, 2], [2, 2], [2, 3], [3, 4], [3, 5], [4, 4], [5, 6], [6, 5], [7, 9], [7, 11], [8, 7], [8, 9]])
# 执行PAM聚类
k = 3
medoids, clusters = pam_clustering(data, k)
# 输出结果
print("Medoids:", medoids)
for i in range(k):
print("Cluster", i+1, ":", data[clusters[i]])
以上代码实现了一个简单的PAM聚类算法,用于对给定的二维数据进行聚类。代码中的pam_clustering
函数接受数据集、簇的个数和最大迭代次数作为输入,并返回选择出的medoids以及对应的簇划分。
总结
PAM聚类算法是一种常见的聚类算法,它通过选择代表性的样本点作为簇的中心,并通过最小化总距离的方式来划分数据点。本文介绍了PAM聚类算法的原理,并使用Python实现了一个简单的PAM聚类算法示例。读者可以根据自己的需求和数据特点,使用PAM聚类算法对数据进行聚类分析。