GIS:地理信息系统

1.Geometry

Geometry是所有此扩展中类型得基类,其他类型如Point,LineString,Polygon都是Geometry的子类。

Geometry有一些属性,这些属性是所有其他几何类的共有属性
type:  类型(Point, LineString,…)
SRID:  该值确定了用于描述定义几何对象的坐标空间的空间坐标系统
coordinates:  坐标值
interior, boundary, exterior:  interior是几何对象所展空间的部分,boundary是几何对象的边界
exterior是几何对象未占有的空间。
MBR: 能够覆盖几何对象的最小矩形,可以想象成信封,它由几何对象中最大最小的坐标值组合而成:
((MINX MINY, MAXX MINY, MAXX MAXY, MINX MAXY, MINX MINY))
simple/nonsimple: 几何对象是否简单
closed/not closed: 几何对象是否封闭
dimension: 维度数(Point: 0, LineString: 1, Polygon: 2)

1.1 Point

顾名思义就是点,有一个坐标值,没有长度、面积、边界。

1.2 LineString

顾名思义就是线,由一系列点连接而成。
如果线从头至尾没有交叉,那就是简单的(simple)
如果起点和终点重叠,那就是封闭的(closed)

1.3 Polygon

多边形。可以是一个实心平面形,即没有内部边界,也可以有空洞,类似纽扣。

1.4 MultiPoint, MultiLineString, MultiPolygon, GeometryCollection

这4种类型都是集合类,是多个Point、LineString或Polygon组合在一起而成。

2. 几何对象在MySQL中的数据格式

在MySQL中有3种表达几何对象的格式:
—>WKT(文本格式)
—>WKB(二进制格式)
—>MySQL内部存储格式
其中WKT格式简单易读,在这里着重介绍:

2.1 WKT

2.1.1 Point

  1. POINT(121.213342 31.234532)

经度(longitude)在前,维度(latitude)在后,用空格分隔

2.1.2 LineString

LINESTRING(121.342423 31.542423,121.345664 31.246790,121.453178 31.456862)

点与点之间用逗号分隔;一个点中的经纬度用空格分隔,与POINT格式一致

2.1.3 Polygon

POLYGON((121.342423 31.542423,121.345664 31.246790,121.453178 31.456862),
        (121.563633 31.566652,121.233565 31.234565,121.568756 31.454367))

由一个表示外部边界的LineString和0个或多个表示内部边界的LineString组成,最简单的就是只有一个外边界的情况:POLYGON((0 0,10,0 10 10, 0 10))

2.1.4 集合类格式

MULTIPOINT(0 0, 20 20, 60 60)
MULTILINESTRING((10 10, 20 20), (15 15, 30 15))
MULTIPOLYGON(((0 0,10 0,10 10,0 10,0 0)),((5 5,7 5,7 7,5 7, 5 5)))
GEOMETRYCOLLECTION(POINT(10 10), POINT(30 30), LINESTRING(15 15, 20 20))

3. 几何对象创建函数

MySQL表中的几何对象有它自己的内部格式,我们需要将几何对象从方便输入的WKT格式转换为其内部格式,才能进行进一步的存储,计算等。
这里主要讲解使用WKT格式的函数,对于集合类对象的创建函数由于较少使用也不再列举
GeomFromText(wkt): 创建一个任何类型的几何对象Geometry
PointFromText(wkt): 创建一个Point对象
LineStringFromText(wkt): 创建一个LineString对象
PolygonFromText(wkt): 创建一个Polygon对象

4. 测试

4.1 创建表

t_geo_test  CREATE TABLE `t_geo_test` (
  `ID` int(11) NOT NULL,
  `NAME` varchar(64) NOT NULL,
  `SHAPE` geometry NOT NULL,
  PRIMARY KEY (`ID`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1

4.2 插入数据

插入点
INSERT INTO `t_geo_test` (ID,NAME,SHAPE) VALUES 
    (1, 'P1', geomFromText('POINT(121.474103 31.232862)'));

插入线
INSERT INTO `t_geo_test` (ID,NAME,SHAPE) VALUES 
    (2, 'L1', geomFromText('LINESTRING(121.474103 31.232862,121.472462 31.231339,121.471984 31.232821)'));

插入多边形
INSERT INTO `t_geo_test` (ID,NAME,SHAPE) VALUES 
    (5, 'POLYGON_1', geomfromtext('POLYGON((121.474243 31.234504, 121.471775 31.233348, 121.470724 31.23155, 121.471603 31.230229, 121.472655 31.230357, 121.475777 31.232045, 121.474243 31.234504))'));

image.png

4.3 获取数据

5. 常用函数

5.1 获取几何对象属性的函数

5.1.1 Geometry

-->Dimension(g)
返回对象g的维数
-->Envelope(g)
返回对象g的最小边界矩形(MBR)。结类型为Polygon值。
-->GeometryType(g)
以字符串形式返回几何类型的名称,如POINT,LINESTRING
-->IsClosed(g)
返回对象g是否封闭
-->IsSimple(g)
返回对象g是否简单

5.1.2 Point

-->X(p)
以双精度数值返回点p的X坐标值(经度)。
-->Y(p)
以双精度数值返回点p的Y坐标值(纬度)。

5.1.3 LineString

-->EndPoint(line)
返回对象line的最后一个点Point
-->StartPoint(line)
返回对象line的第一个点Point
-->PointN(line, N)
返回对象line中第N个点,N从1开始

5.1.4 Polygon

-->ExteriorRing(poly)
返回对象poly的外环,类型为LineString
-->InteriorRingN(poly, N)
返回对象poly的第N个内环,N从1开始
-->NumInteriorRings(poly)
返回对象poly的内环个数

5.2 从现成几何对象创建新的对象

5.2.1 st_union(g1, g2)

将g1和g2合并为一个集合类对象

SET @g1 = geomFromText('POLYGON((121.474243 31.234504,121.471775 31.233348,121.470724 31.23155,121.471603 31.230229,121.472655 31.230357,121.475777 31.232045,121.474243 31.234504))');
SET @g2 = geomFromText('POLYGON((121.474243 31.234804,121.471775 31.233948,121.471724 31.23155,121.471903 31.230229,121.472655 31.230157,121.475777 31.231045,121.474243 31.234804))');
SELECT st_union(@g1, @g2);

5.2.2 st_difference(g1, g2)

返回几何对象,该对象表示了几何值g1与g2的点集合差异

SET @g1 = geomFromText('POLYGON((121.474243 31.234504,121.471775 31.233348,121.470724 31.23155,121.471603 31.230229,121.472655 31.230357,121.475777 31.232045,121.474243 31.234504))');
SET @g2 = geomFromText('POLYGON((121.474243 31.234804,121.471775 31.233948,121.471724 31.23155,121.471903 31.230229,121.472655 31.230157,121.475777 31.231045,121.474243 31.234804))');
SELECT st_difference(@g1,@g2);

5.2.3 st_intersection(g1,g2)

返回几何对象,该对象表示了几何值g1与g2的点集合交集

SET @g1 = geomFromText('POLYGON((121.474243 31.234504,121.471775 31.233348,121.470724 31.23155,121.471603 31.230229,121.472655 31.230357,121.475777 31.232045,121.474243 31.234504))');
SET @g2 = geomFromText('POLYGON((121.474243 31.234804,121.471775 31.233948,121.471724 31.23155,121.471903 31.230229,121.472655 31.230157,121.475777 31.231045,121.474243 31.234804))');
SELECT st_intersection(@g1,@g2);

5.3 几何对象之间空间关系的函数

6.3.1 st_contains(g1, g2)

  返回1: g1完全包含g2;返回0: g1未包含g2

6.3.2 st_crosses(g1, g2), st_intersects(g1, g2)

  返回1: g1与g2相交;返回0:g1与g2未相交

6.3.3 st_disjoint(g1, g2)

  是st_crosses的反函数

6.3.4 st_within(g1, g2)

  g1在g2内则返回1,否则返回0

6. 空间索引

对表中的geometry类型的字段进行索引可以优化搜索,MySQL中通过对Geometry对象的MBR创建索引创建:

CREATE SPATIAL INDEX i_shape ON t_geo_test(SHAPE);
删除:
DROP INDEX i_shape ON t_geo_test;

7.注意

  • 目前MySQL中支持的空间坐标系统没有gcj02,bd09等国内坐标系,默认使用WGS84地球坐标系,所以在创建几何对象时输入的坐标值尽量使用WGS84坐标,以避免误差。
  • MySQL中的计算距离,长度,面积等绝对数值的空间计算函数(area(), GLength(), st_distance())存在一定的误差,尽量不要使用。