5

4 つの円のデータベースが与えられた場合、各円には半径と地理的に位置付けられた中心があります。

id | radius | latitude | longitude
---+--------+----------+----------
 1 |      3 |    40.71 |    100.23
 2 |     10 |    50.13 |    100.23
 3 |     12 |    39.92 |    100.23
 4 |      4 |    80.99 |    100.23

注: 簡単にするために、各円の経度は同じです。

latitude円 2 にいると仮定すると、 /longitude座標と各円のに従って、近くのすべての円を見つけたいと思いますradius

たとえば、緯度/経度の座標によると、次の順序になります。

  1. 円 1 (近接のため: 9.42 <- 50.13 - 40.71)
  2. 円 3 (近接のため: 10.21 <- 50.13 - 39.92)
  3. 円 4 (近接のため: 30.86 <- 80.99 - 50.13)

しかし、緯度/経度の座標と各円の半径によると、次のようになります。

  1. 円 3 (近接のため: 1.79 <- 12 - 10.21)
  2. 円 1 (近接のため: 6.42 <- 9.42 - 3)
  3. 円 4 (近接のため: 26.86 <- 30.86 - 4)

SQLでこれを行う簡単な方法はありますか?

4

4 に答える 4

1

postgresqlのcontrib で提供されるcubeおよびearthdistance拡張機能は、これを処理して、少なくともおおよその回答を生成できます。具体的には、彼らは地球が単純な球体であると仮定しているため、数学がはるかに簡単になります。

これらの拡張機能を使用すると、次のように円 2 と他の円の間の距離を生成できます。

select circle.id,
       earth_distance(ll_to_earth(circle.latitude, circle.longitude),
                      ll_to_earth(x.latitude, x.longitude))
 from circle,
      circle x
 where x.id = 2 and circle.id <> x.id
 order by 2;

円の半径を修正するには、上記の距離からx.radiusとを差し引くだけcircle.radiusでよいのですが、半径の単位を考える必要があります。既定では、earth_distanceはメートル単位で値を計算します。

ここで、円のリスト全体をスキャンしてそれぞれの距離を計算し、それらを並べ替えて制限する以外のことをクエリにさせることは、はるかに困難です。いくつかのアプローチがあります。

  • 立方体の要点で索引付けする機能を使用して、円の中心の周りの特定のボックス内を検索するための索引を作成できるため、考慮すべき円のリストを削減できます。
  • 円が編集されるたびに、各円と他のすべての円の間の距離を事前に計算し、トリガーを使用してこの計算を別のテーブルに保持します。

2 番目のオプションは、基本的に次のように始まります。

create table circle_distance as
select a.id as a_id, b.id as b_id,
 earth_distance(ll_to_earth(a.latitude, a.longitude),
                ll_to_earth(b.latitude, b.longitude))
 from circle a, circle b
 where a.id <> b.id;
alter table circle_distance add unique(a_id, b_id);
create index on circle_distance(a_id, earth_distance);

次に、 の関連する行を削除/挿入するためのかなり面倒な関数がcircle_distance、 のトリガーによって呼び出されますcircle。これは、次のことができることを意味します。

select b_id from earth_distance where a_id = $circle_id order by earth_distance limit $n

このクエリは、そのインデックスを使用し(a_id,earth_distance)てクイック スキャンを実行できます。

于 2012-07-10T20:38:37.217 に答える
0

ST_Distance車輪の再発明ではなく、PostGIS Geographyデータ型とそれに関連する関数(例:)を確認することをお勧めします

于 2012-07-10T07:39:18.540 に答える