DBSCAN的参数eps,python

3 投票
1 回答
2258 浏览
提问于 2025-04-18 08:47

我有一组点,它们的地理位置(SRID: 4326)存储在一个数据库里。

我得到了一个代码,目的是用DBSCAN算法对这些点进行聚类。参数设置如下:eps=1000,min_points=1。

我得到的聚类结果是距离小于1000米的点。我原以为距离小于1000米的两个点应该属于同一个聚类。那么,eps真的以米为单位吗?

以下是代码:

    self.algorithm='DBSCAN'
    X=self.data[:,[2,3]]
    if self.debug==True:
        print 'Nbr of Points: %d'% len(X)
    # print X.shape
    # print dist_matrix.shape
    D = distance.squareform(distance.pdist(X,'euclidean'))
    # print dist_matrix
    # S = 1 - (D / np.max(D))
    db = DBSCAN(eps, min_samples).fit(D)
    self.core_samples = db.core_sample_indices_
    self.labels = db.labels

我并不是想找其他方法来运行这个代码,而是想真正理解eps的值。它在距离上代表什么。min_sample设置为1是因为我接受聚类的大小可以是1个样本。

1 个回答

3

这要看你是怎么实现的。

你的距离函数可以返回任何单位的距离,比如米、毫米、码、公里、英里、度数等等,但你没有告诉我你用的是什么函数来计算距离!如果我没记错的话,SRID: 4326并不影响距离计算。

sklearn中使用的"haversine"似乎是用度数来计算的,而不是米。

无论如何,min_points=1这个设置是没有意义的。查询点本身就被算作一个点,所以每个点自己就是一个聚类。如果min_points <= 2,那么DBSCAN的结果将是单链接聚类。要得到基于密度的聚类,你需要选择一个更高的值来获得真实的密度。

你可能想用ELKI的DBSCAN。根据他们的Java源代码,他们的距离函数使用的是米,而且他们的R*-树索引可以加速范围查询,这样会大大提高速度(从O(n^2)变成O(n log n))。

撰写回答