天天看点

postgis学习笔记

一、Transforming from SRID 900913 to 4326 with PostGis

ALTER TABLE planet_osm_point ALTER COLUMN way TYPE geometry(Point,4326) USING ST_Transform(way,4326);

二、用postgis查找指定范围内的兴趣点

SELECT t.osm_id,ST_astext(t.way) FROM planet_osm_point t 

WHERE ST_DWithin(

ST_Transform(ST_GeomFromText('POINT(1.99 7.18)',4326),26986),

ST_Transform(t.way,26986), 1516) 

ORDER BY ST_Distance(ST_GeomFromText('POINT(-87.71 43.741)',4326), t.way);

ST_Distance:即给定两个空间点计算两点间的距离。计算结果的单位与你的空间数据的参考系有关。

如果你使用的是4326(wgs84)这个坐标系的话他是以度为单位的。要想转成米为单位的话还得做一个转换,下面会提到:

GEOCS代表的是地理坐标系,也就是以经纬度表示的坐标系统,例如4326;

PROJCS代表的是投影坐标系,它是通过一种算法把球面坐标系转成平面坐标系,以便计算,一般是以米为单位表示,例如26986;

因此,在求两点之间的距离时,由于存的数据都是经纬度,因此它参考的是GEOS,要想得到以米为单位的结果,首先要把它转成PROJCS,可以通过ST_Transform来实现。

查看postgis手册geometry ST_Transform(geometry g1, integer srid);

第一个参数是原来的几何对象。第二个参数为要把他转换到这个投影所代表的坐标系下。

这时我们只要找一个单位是米的投影坐标系把他转换过去就好了,例如:

SELECT ST_Distance(

   ST_Transform(ST_GeomFromText('POINT(-87.734087560562 43.770129071141)',4326),26986),

   ST_Transform(ST_GeomFromText('POINT(-87.747382933006 43.759234252055)', 4326),26986)

  );

这个查出来的结果即是以米为单位的两点间的距离了。

现在在说如何查找一定范围内的点。

这里用到了postgis里的这个函数:boolean ST_DWithin(geometry g1, geometry g2, double precision distance_of_srid);

第一个参数为参考对象,第二个参数为目标对象,第三个参数为距离(同样如果是地理坐标系单位是度。投影坐标系单位是米)。

即以g1为中心,半径为distance_of_srid,这个范围内包不包含g2,如果包含返回true,否则即为假。

如下给了一个完整的例子。查找以(-87.71 43.741)为中心半径1516米范围内的兴趣点,之后按与这个中心点由近到远的顺序排列结果。

SELECT t.feat_id,astext(t.geometry) FROM gis_site t 

WHERE ST_DWithin(

ST_Transform(GeomFromText('POINT(-87.71 43.741)',4326),26986),

ST_Transform(t.geometry,26986), 1516) 

ORDER BY ST_Distance(GeomFromText('POINT(-87.71 43.741)',4326), t.geometry);

结果:

24;"POINT(-87.718330082111 43.753078987035)"

17;"POINT(-87.726085716036 43.736952192682)"

18;"POINT(-87.726085716036 43.736952192682)"

找到了三个点

三、osm2pgsql --create --cache 2048 --style /usr/local/share/osm2pgsql/default.style --database postgis /home/benin-latest.osm.