学习Python中的DBSCAN算法聚类

421 阅读6分钟

Python中的DBSCAN算法聚类法

DBSCAN是一种流行的基于密度的数据聚类算法。为了对数据点进行聚类,该算法将数据的高密度区域与低密度区域分开。与K-Means算法不同,这种算法最好的地方在于我们不需要事先提供所需的聚类数量。

Python中的DBSCAN算法

DBSCAN算法根据距离测量对点进行分组,通常是欧氏距离最小的点数。这种算法的一个基本属性是,它可以帮助我们追踪离群点,即低密度区域的点;因此它对离群点不敏感,就像K-Means聚类那样。

前提条件

要想继续学习,读者需要以下条件。

  1. 在你的系统中安装Python,或者访问Google Colab。
  2. 以CSV文件形式提供的数据集。

简介

DBSCAN算法有两个参数。

这些参数是。

  1. Epsilon(Eps):这是两个点被称为邻居所需的最小距离。这个距离被称为Epsilon(Eps)。因此,我们认为Eps是考虑两点为邻居的门槛,即,如果两点之间的距离是最多的Eps,那么我们认为这两点是邻居。

  2. 最小点(MinPoints):这指的是构建一个聚类所需的最小点数。我们认为MinPoints是将一个聚类视为一个聚类的门槛。只有当点的数量大于或等于MinPts时,一个聚类才被认可。

我们根据上述两个参数将数据点分为三类。因此,让我们来看看这些类别。

DBSCAN聚类中的数据点类型

在DBSCAN聚类完成后,我们最终有以下三种类型的数据点。

  1. 核心:这是一个上面两个参数完全确定的点,即至少有MinpointsEps距离内的点,从这个点开始。
  2. 边界:这是不属于核心点的任何数据点,但它至少有一个核心点在与自己的Eps距离之内。
  3. 噪声:这是一个在与自己的距离Eps内少于Minpoints的点。因此,它不是一个核心边界

现在让我们来看看DBSCAN聚类的算法步骤。

DBSCAN算法

以下是DBSCAN聚类的算法步骤。

  • 第1步:最初,算法从数据集中随机选择一个点(x),并从该点找到所有在Eps范围内的邻居点。如果Eps-邻居的数量大于或等于MinPoints,我们就认为x是一个核心点。然后,与它的Eps邻居一起,x形成了第一个聚类。

在创建第一个聚类后,我们检查其所有成员点并找到它们各自的Eps邻居。如果一个成员至少有MinPoints Eps邻居,我们就将这些Eps邻居加入到集群中,从而扩大初始集群。这样继续下去,直到没有更多的点可以加入到这个集群中。

  • 第2步:对于任何其他没有分配到集群的核心点,创建一个新的集群。

  • 第3步:对核心点集群,找到并分配所有与之递归连接的点。

  • 第4步:遍历数据集中所有未被关注的点,并将它们分配到离自己最近的Eps距离的集群中。如果一个点不适合任何可用的聚类,就把它定位为一个噪声点。

DBSCAN的Python实现

如同任何实施方法一样,我们从获取数据集开始,为我们的模型实施做好准备。

数据预处理

导入所需的库

让我们从导入所需的库开始,以便在算法上实施。

import numpy as np
import matplotlib.pyplot as plt
import pandas as pd
data = pd.read_csv("/content/drive/MyDrive/Mall_Customers.csv") # importing the dataset

探索性数据分析

这是调查现有数据的过程,并在图形表示和统计总结的帮助下确定模式中的不一致和其他异常情况。

  • 检查数据的头部。
data.head()
  • 输出

dataset head

  • 检查数据集的形状。
print("Dataset shape:", data.shape)

输出

Dataset shape: (200, 5)

接下来,我们检查数据集是否有任何缺失值。

# checking for NULL data in the dataset
data.isnull().any().any()

输出

False

上述输出意味着在我们的数据集中没有缺失值。由于我们的数据已经准备好了,让我们提取Annual IncomeSpending Score 列,并对它们应用我们的DBSCAN模型。

# extracting the above mentioned columns
x = data.loc[:, ['Annual Income (k$)',
                 'Spending Score (1-100)']].values
  • 让我们检查一下x的形状。
print(x.shape)

输出

(200, 2)

在我们应用DBSCAN模型之前,首先,我们需要获得它的两个参数。

  1. MinPoints:我们可以获得用于识别集群的最小点数,如下所示。
  • 如果数据集有两个维度,则使用每个簇的最小样本数为4。
  • 如果数据有两个以上的维度,则每个聚类的最小样本应该是。Min_sample(MinPoints) = 2 * Data dimension

由于我们的数据是二维的,我们将使用默认值4作为我们的MinPoint参数。

  1. Epsilon(Eps):为了计算Eps的值,我们将使用最近的邻居(Nearest Neighbours)来计算每个数据点与它最近的邻居之间的距离。之后,我们对它们进行排序,最后将其绘制出来。从该图中,我们确定图形曲率处的最大值。这个值就是我们的Eps

使用最近的邻居计算数据之间的接近程度

from sklearn.neighbors import NearestNeighbors # importing the library
neighb = NearestNeighbors(n_neighbors=2) # creating an object of the NearestNeighbors class
nbrs=neighb.fit(x) # fitting the data to the object
distances,indices=nbrs.kneighbors(x) # finding the nearest neighbours

排序和绘制数据点之间的距离

# Sort and plot the distances results
distances = np.sort(distances, axis = 0) # sorting the distances
distances = distances[:, 1] # taking the second column of the sorted distances
plt.rcParams['figure.figsize'] = (5,3) # setting the figure size
plt.plot(distances) # plotting the distances
plt.show() # showing the plot

输出

执行上面的代码,我们得到下面的图。

plot

从上面的图中,我们注意到曲线的最大曲率约为8,因此我们选择Eps为8。

现在我们的两个参数是:

  • MinPoints = 4
  • Eps = 8

现在我们有了这些参数,让我们来实现DBSCAN模型。

实施DBSCAN模型

from sklearn.cluster import DBSCAN
# cluster the data into five clusters
dbscan = DBSCAN(eps = 8, min_samples = 4).fit(x) # fitting the model
labels = dbscan.labels_ # getting the labels
# Plot the clusters
plt.scatter(x[:, 0], x[:,1], c = labels, cmap= "plasma") # plotting the clusters
plt.xlabel("Income") # X-axis label
plt.ylabel("Spending Score") # Y-axis label
plt.show() # showing the plot

聚类图

clusters plot

结语

在这篇文章中,我们已经介绍了DBSCAN算法。首先,我们看了它的关键参数以及这个算法是如何对数据点进行聚类的。我们还了解了与DBSCAN算法相关的三个数据点。后来我们看了如何实现这个算法。