【问题标题】:Find top K most common locations for geo spatial data in SQL server在 SQL Server 中查找地理空间数据的前 K 个最常见位置
【发布时间】:2019-02-03 22:01:52
【问题描述】:

我们拥有地理空间性质的用户数据(纬度、经度)。我们使用 SQL 服务器来存储这个(几何数据类型)。是否有任何实现来了解用户访问的前 k 个最受欢迎的位置(地理数据)。假设我们以 100m 为半径,并将其中的所有点都考虑到同一位置。这基本上意味着对所有用户位置进行聚类并找到最填充的聚类。

就像标量值一样,我们在表上进行分组以找出出现次数最多的条目。我如何为地理数据实现这一目标?

【问题讨论】:

  • 如果是纬度/经度,你为什么用geometry而不是geography
  • 另外,举一个极其荒谬的例子,我们存储了一系列点,每个点相距 90m,一直围绕赤道(如果不能被 90 整除,则需要进行任何伪造来完成圆)。每个点都在其他两个点的 90m 范围内,但你如何确定一个集群的位置?
  • @Damien_The_Unbeliever,感谢您的回复。是的,我考虑过这一点,但是对于实际数据点,例如在城市中四处旅行的用户,有理由认为在他的家庭和办公室位置周围形成了几个集群,对吗?我们目前正在计算级别解决这个问题,但我很想知道是否有办法在数据库级别解决它。

标签: sql sql-server geometry geospatial


【解决方案1】:

地理哈希可以用来解决这个问题,这是一种用哈希表示地球区域的方法。 Google 的 S2 库是一个有效的实现。

使用 S2,您可以执行以下操作:

  1. 将每个点分配给代表区域的给定 S2 CellId(您可以将其调整为不同的区域级别,范围从 a face of the Earth to something smaller than your fingertip

  2. 在检索时,对于给定点,将其转换为 S2 CellId 并将其分解为处于索引级别的 S2 CellId。然后使用简单的SELECT * FROM points WHERE point.s2_cell_id IN $RETRIEVAL_IDS

  3. 获取所有“集群”

这是一个使用Node S2 library 构建索引的快速示例:

const s2 = require('@radarlabs/s2');

const user1LongLat = [-73.95772933959961, 40.71623280185081];
const user2LongLat = [-73.95927429199219, 40.71629785715124];
const user3LongLat = [-73.99206161499023, 40.688708709249646];

const user1S2 = ["user1", new s2.CellId(new s2.LatLng(user1LongLat[1], user1LongLat[0])).parent(13)];
const user2S2 = ["user2", new s2.CellId(new s2.LatLng(user2LongLat[1], user2LongLat[0])).parent(13)];
const user3S2 = ["user3", new s2.CellId(new s2.LatLng(user3LongLat[1], user3LongLat[0])).parent(13)];

const groups = {};
[user1S2, user2S2, user3S2].forEach(([userId, cellId]) => {
  const group = groups[cellId.token()] || [];
  group.push(userId);
  groups[cellId.token()] = group;
});

console.log(groups); // { '89c2595c': [ 'user1', 'user2' ], '89c25a4c': [ 'user3' ] }

现在它只是一个简单的查找。 S2 可以将给定区域转换为 S2 单元格,因此您可以按单个点或区域进行查询。

您可以可视化this on the map here

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2022-01-10
    • 2016-08-21
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2017-10-16
    相关资源
    最近更新 更多