如何创建在PostGIS的米一圈?(How to create a circle in meters

2019-07-05 06:35发布

我想问一下如何创建一个圆radius=4km 。 我曾尝试ST_Buffer功能,但它创造一个更大的圈子。 (我看通过将其多边形到一个新的KML文件创建的圈子。)

这就是我努力。

INSERT INTO camera(geom_circle) VALUES(geometry(ST_Buffer(georgaphy(ST_GeomFromText('POINT(21.304116745663165 38.68607570952619)')), 4000)))

圆的中心是一个经度纬度点,但我不知道它的SRID ,因为我已经从一个KML文件导入它。 我需要的SRID以改造几何等?

Answer 1:

KML文件总是纬度/长,使用SRID = 4326。 如果您使用此SRID是隐含的geography 。 地理是混合式4公里的度量指标上拉/长数据的好办法...优秀您是否尝试过这个!

试试这个语句修复了石膏,并使用参数的构造函数点:

SELECT ST_Buffer(ST_MakePoint(21.304116745663165, 38.68607570952619)::geography, 4000);

如果你需要投这回的几何形状,增加::geometry投进行到底。


更新的准确性

以前的答案内部重新项目的几何形状(通常情况下),以该点适合内的UTM区(见ST_Buffer )。 这可能会导致轻微的失真,如果点是在两个边界UTM的边缘。 大多数人不会在乎这些错误的大小,但它往往是几米。 但是,如果您需要亚毫米精确度,可考虑建立一个动态的等距方位投影 。 这需要PostGIS的2.3的ST_Transform ,并从适应另一种答案 :

CREATE OR REPLACE FUNCTION geodesic_buffer(geom geometry, dist double precision,
                                           num_seg_quarter_circle integer)
  RETURNS geometry AS $$
  SELECT ST_Transform(
    ST_Buffer(ST_Point(0, 0), $2, $3),
      ('+proj=aeqd +x_0=0 +y_0=0 +lat_0='
       || ST_Y(ST_Centroid($1))::text || ' +lon_0=' || ST_X(ST_Centroid($1))::text),
      ST_SRID($1))
  $$ LANGUAGE sql IMMUTABLE STRICT COST 100;
CREATE OR REPLACE FUNCTION geodesic_buffer(geom geometry, dist double precision)
  RETURNS geometry AS 'SELECT geodesic_buffer($1, $2, 8)'
  LANGUAGE sql IMMUTABLE STRICT COST 100;
-- Optional warppers for geography type
CREATE OR REPLACE FUNCTION geodesic_buffer(geog geography, dist double precision)
  RETURNS geography AS 'SELECT geodesic_buffer($1::geometry, $2)::geography'
LANGUAGE sql IMMUTABLE STRICT COST 100;
CREATE OR REPLACE FUNCTION geodesic_buffer(geog geography, dist double precision,
                                           num_seg_quarter_circle integer)
  RETURNS geography AS 'SELECT geodesic_buffer($1::geometry, $2, $3)::geography'
  LANGUAGE sql IMMUTABLE STRICT COST 100;

一个简单的例子来运行的功能之一是:

SELECT geodesic_buffer(ST_MakePoint(21.304116745663165, 38.68607570952619)::geography, 4000);

而到了距离比较每个缓冲点,这里是每一个的长度测 (上旋转椭圆最短路径,即WGS84)。 首先这个功能:

SELECT count(*), min(buff_dist), avg(buff_dist), max(buff_dist)
FROM (
  SELECT ST_Distance((ST_DumpPoints(geodesic_buffer(poi, dist)::geometry)).geom, poi) AS buff_dist
  FROM (SELECT ST_MakePoint(21.304116745663165, 38.68607570952619)::geography AS poi, 4000 AS dist) AS f
) AS f;

 count |      min       |       avg       |      max
-------+----------------+-----------------+----------------
    33 | 3999.999999953 | 3999.9999999743 | 4000.000000001

与此相比,ST_Buffer(答案的第一部分),这表明它由约一点五六M的关闭:

SELECT count(*), min(buff_dist), avg(buff_dist), max(buff_dist)
FROM (
  SELECT ST_Distance((ST_DumpPoints(ST_Buffer(poi, dist)::geometry)).geom, poi) AS buff_dist
  FROM (SELECT ST_MakePoint(21.304116745663165, 38.68607570952619)::geography AS poi, 4000 AS dist) AS f
) AS f;

 count |      min       |       avg        |      max
-------+----------------+------------------+----------------
    33 | 4001.560675049 | 4001.56585986067 | 4001.571105793


文章来源: How to create a circle in meters in postgis?