空间索引减慢了查询mysql

时间:2016-01-16 11:51:26

标签: mysql performance indexing spatial duration

你好我有一个问题。

我有一个表格,其中时间是一个索引。我的select语句如下所示:

select count(*) from sometable
   where
      time between @startTime and @endTime
      and
      st_intersects(location,@somePolygon);

此查询需要60秒才能运行。该表包含超过5000万行,所以我认为这是可以的。但现在如果我添加位置和索引查询需要90秒才能运行。为什么放慢速度?而不是加速?

//更新 您好,感谢四位反馈。

用索引解释

 id | select_type | table  | partitions | type  | possible_keys | key  | key_len | ref  | rows    | filtered | Extra
  1 | SIMPLE      | q1_geo | NULL       | range | ORT, Zeit     | Zeit |       5 | NULL | 6454092 |   100.00 | Using index condition; Using where

且没有

id | select_type | table  | partitions | type  | possible_keys | key  | key_len | ref  | rows    | filtered | Extra
 1 | SIMPLE      | q1_geo | NULL       | range | Zeit          | Zeit |       5 | NULL | 6454092 |   100.00 | Using index condition; Using where

//更新

版本:' 5.7.5-m15' Engien:MyISAM

表,创建表

CREATE TABLE `q1_geo` (
  `ID` int(11) NOT NULL,
  `ZEIT` datetime NOT NULL,
  `R_ID` bigint(20) NOT NULL AUTO_INCREMENT,
  `ORT` point NOT NULL,
  PRIMARY KEY (`ID`,`ZEIT`,`R_ID`),
  KEY `Zeit` (`ZEIT`),
  KEY `Ort` (`ORT`(25))
) ENGINE=MyISAM AUTO_INCREMENT=842057641 DEFAULT CHARSET=latin1

1 个答案:

答案 0 :(得分:2)

你在这里遇到了一个有趣的MySQL索引问题。当您在time上使用简单索引时,您的查询会对该索引执行范围扫描,然后为该范围内的每一行计算st_intersects()

但是,当您在location MySQL的查询计划程序上添加第二个地理索引时(发布您的EXPLAIN!发布您的表定义!)会执行两次索引扫描,然后索引合并。

您无法制作地理位置和普通列的复合索引。

要加快此查询,您需要了解的另一件事是您的时间标准或空间标准是否更具选择性。哪一个会将您的数据集缩小到较少的结果?那是你想要首先索引的那个。

你如何解决这个问题?如果你可以将location geo变量划分为两个单独的列(它们可能是x和y,或lat和long),那么将时间x和y放入复合索引中,然后执行以下操作:

WHERE  time >= @startTime
  AND  time <= @endTime
  AND  x >= MinX(@polygon)
  AND  x <= MaxX(@polygon)
  AND  y >= MinY(@polygon)
  AND  y <= MaxY(@polygon)
  AND  st_intersects(location, @somePolygon)

您需要在多边形参数上计算出Min和Max函数。

这个技巧的关键是允许你将一些(如果不是所有你的空间信息)放入一个普通的复合索引而不是一个独立的地理索引。

相关问题