расширенный (?) выборочный запрос postgis - PullRequest
1 голос
/ 24 июня 2011

Проблема: мне нужно выбрать для каждого здания в моей таблице, в котором есть, по крайней мере, 2 аптеки и 2 учебных центра в радиусе 1 км, все POI (аптеки, торговые центры, медицинские центры, образовательные центры, полицейские участки пожарные станции), которые находятся в пределах 1 км от соответствующего здания. структура таблицы ->

здание (серийный номер, имя varchar)

poi_category (id serial, cname varchar) --cname является именем категории курса

poi (серийный номер, имя varchar, целое число c_id) - c_id - FK, ссылающийся на poi_category (id)

все столбцы координат имеют геометрию типа, а не географию (назовем их geom)

вот как я думал, что это должно быть сделано, но я не уверен, что это даже правильно, не говоря уже об оптимальном решении этой проблемы

SELECT r.id_b, r.id_p
FROM (
     SELECT b.id AS id_b, p.id AS id_p, pc.id AS id_pc,pc.cname
     FROM building AS b, poi AS p, poi_category AS pc
     WHERE ST_DWithin(b.geom,p.geom, 1000) AND p.c_id=pc.id
     ) AS r,
     (
     SELECT * FROM r GROUP BY id_b
     ) AS r1

 HAVING  count (
                   SELECT *
                   FROM r, r1
                   WHERE r1.id_b=r.id_b AND r.id_pc='pharmacy'

                )>1
             AND
             count (
                   SELECT *
                   FROM r, r1
                   WHERE r1.id_b=r.id_b AND r.id_pc='ed. centre'

                )>1

Это способ пойти на то, что мне нужно? Какое решение будет лучше с точки зрения производительности? Как насчет самого элегантного решения? Я также разместил здесь: http://gis.stackexchange.com/questions/11445/postgis-advanced-selection-query

1 Ответ

3 голосов
/ 16 августа 2012

Это решение, которое я разработал.Это самый быстрый, который я смог найти, но он все еще медленный.Учитывая характер задачи, я сомневаюсь, что она может быть выполнена быстрее ...

WITH 
building AS (
  SELECT way, osm_id
  FROM osm_polygon
  WHERE tags @> hstore('building','yes')
  --ORDER BY 1 
  LIMIT 1000
),
pharmacy AS (
  SELECT way
  FROM osm_poi
  WHERE tags @> hstore('amenity','pharmacy') 
), 
school AS (
  SELECT way 
  FROM osm_poi
  WHERE tags @> hstore('amenity','school') 
)
SELECT ST_AsText(building.way) AS geom, building.osm_id AS label
FROM building
WHERE
  (SELECT count(*) > 1
   FROM pharmacy
   WHERE ST_DWithin(building.way,pharmacy.way,1000))
  AND
  (SELECT count(*) > 1
   FROM school
   WHERE ST_DWithin(building.way,school.way,1000))

Ваша.S.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...