基于划分的聚类算法(K-Means)与基于密度的聚类算法(DBSCAN)对比分析
在开始阅读前可以看一下有关这两个算法的描述和可视化效果展示
Visualizing K-Means Clustering
Visualizing DBSCAN Clustering
使用Python实现了两个算法,算法设计场景是对平面二维样本点的计算
算法思想
K-Means算法步骤
- 随机生成k个点作为样本数据的中心点
- 计算所有点分别到k个中心点的距离
- 对于二维的每个样本点,比较到哪一个中心点的距离近(欧式距离最小),就被划分到哪一类,并更新样本点的类别表
- 对于归类后的数据重新计算中心点的坐标
- 判断中心点是否有明显变化,如果有,跳转到2,如果没有,跳转到6
- 程序结束,划分完成
DBSCAN算法步骤
- 设置与样本集等长的访问标记列表(最初所有的点被标记为noise或unvisted)
- 设置邻域epsilon,点邻域形成团的最少点数量 min_points
- 遍历样本点集D, 检查点p的表示是否visited,如果unvisited,执行4,否则继续进行遍历直到结束
- 检查距p在epsilon范围内的点数量是否达到min_points,如果是,则跳转到5
- 将邻域内所有点加入到该群集clusters中
- 检查这些点在其邻域内是否有不少于min_points的点,如果是,递归扩充该群集
- 完全有可能选择的点在其epsilon球中少于minPoints,并且也不属于任何其他群集。如果是这种情况,则将其视为不属于任何群集的“噪声点”。
算法实现
K-Means算法实现
# 计算两点之间的距离,传入narray作为[[],[],[]]做多个点距离计算,axis=1
def dist(a, b, axis=1):
return np.linalg.norm(a - b, axis=axis)
def kmeans_alg(k, D):
"""
params:
k 设定划分的区域数目
D 样本点数据集
"""
# 随机初始化中心点 方法一
center_x = np.random.randint(D.min(0)[0], D.max(0)[0], size=k)
center_y = np.random.randint(D.min(0)[1], D.max(0)[1], size=k)
centers = np.array(list(zip(center_x, center_y)), dtype=D[:,0].dtype)
# 随机初始化中心点 方法二
centers = D[np.random.randint(0, len(D), size=k)]
# c_new用来保存迭代产生的新中心点坐标
centers_new = np.zeros(centers.shape)
# 用于保存数据所属划分
labels = np.zeros(len(D))
# 设置容忍度,该变量为迭代前后中心点的变化明显性,低于这个明显性的时候,不再进行迭代
tol_move = 10.0
tol = True
while tol:
for i in