对于地理位置储存,在如今的项目中用的愈来愈多,支持的数据库也很多,像mangodb,redis-geo,postgreSQL..... 本文对postgreSQL point 类型对地理位置数据插入,索引,附近查询,进行测试;因为电脑配置不高,仅仅插入600多万条数据进行测试,但测试结果为什么还不如那位大神上100亿测试的数据快。(下面解释为)php
create table tbl_point(id serial8, poi point);
alter sequence tbl_point_id_seq cache 10000;
insert into tbl_point(poi) select point(trunc(100000*(0.5-random())), trunc(100000*(0.5-random()))) from generate_series(1,10000);
insert into tbl_point(poi) select point(trunc(100000*(0.5-random())), trunc(100000*(0.5-random()))) from generate_series(1,100000);
insert into tbl_point(poi) select point(trunc(100000*(0.5-random())), trunc(100000*(0.5-random()))) from generate_series(1,1000000);
insert into tbl_point(poi) select point(trunc(100000*(0.5-random())), trunc(100000*(0.5-random()))) from generate_series(1,4000000);
\dt+ tbl_point
create index idx_tbl_point on tbl_point using gist(poi) with (buffering=on); //建立索引 \di+ //查看索引信息
select *,poi <-> point(1000,1000) dist from tbl_point where poi <-> point(1000,1000) < 100 order by poi <-> point(1000,1000) limit 10;
就是换个位置数据继续查10条。redis
select *,poi <-> point(4000,7000) dist from tbl_point where poi <-> point(4000,7000) < 100 order by poi <-> point(4000,7000) limit 10;
刚才两次查询效率都不错,都是1毫秒多一点,来看看查50条记录效果。数据库
select *,poi <-> point(4000,7000) dist from tbl_point where poi <-> point(4000,7000) < 100 order by poi <-> point(4000,7000) limit 50;
查50条记录效果几乎到了不理想的状态,咱们再把limit去掉,直接查询所有看看。dom
select *,poi <-> point(4000,7000) dist from tbl_point where poi <-> point(4000,7000) < 100 order by poi <-> point(4000,7000);
发现竟然快了不少不少post
回答上面咱们的疑问:当数据足够时,咱们只查询10条时,并无扫描全盘,找到10条就返回,全部都是1ms 左右,那速度是至关的快。 因此,别人600亿的数据找10条速度理想就能够理解了。测试
而当须要返回50条数据时,知足要求的并无那么多,必然全盘扫描,而且屡次核对。形成查询时间达到10条查询时间的36000多倍。。。。。。。。实乃恐惧。。。code
最后奇怪的事情发生了,我执行所有查询,不添加 limit 50, 速度又快了不少不少。这个问题我也不是很懂,请各位赐教。blog
原创做者:邵泽明 原文连接:http://blog.4d4k.com/index.php/archives/46/索引