【发布时间】:2021-07-16 23:52:47
【问题描述】:
我有一个带有纬度和经度值的英国邮政编码数据库。我有一个查询,允许我传入一个以英里为单位的数字、lat 和 lng 值,它会找到以英里为单位的半径内的所有行。这可行,但查询很慢。
表中有 1 778 632 行,我为所有列添加了索引,但对执行速度没有任何影响。
Mysql 5.7.29 版本正在使用中。
有什么方法可以加快以下逐字查询的执行速度?
SELECT id,postcode, ROUND((
3959 * acos (
cos ( radians(56.007165000) )
* cos( radians( latitude ) )
* cos( radians( longitude ) - radians(-3.784005000) )
+ sin ( radians(56.007165000) )
* sin( radians( latitude ) )
)
),1) AS distance
FROM postcodelatlng
HAVING distance <= 10
ORDER BY distance
所以我更新了原始查询以添加这样的绑定框:
SELECT id,postcode, ROUND((
3959 * acos (
cos ( radians(56.007165000) )
* cos( radians( latitude ) )
* cos( radians( longitude ) - radians(-3.784005000) )
+ sin ( radians(56.007165000) )
* sin( radians( latitude ) )
)
),1) AS distance
FROM postcodelatlng
WHERE latitude BETWEEN 56.007165000 - 10/69.172
AND 56.007165000 + 10/69.172
AND longitude BETWEEN -3.784005000 - 10/69.172 / COS(RADIANS(56.007165000))
AND -3.784005000 + 10/69.172 / COS(RADIANS(56.007165000))
HAVING distance <= 10
ORDER BY distance
--
-- Table structure for table `postcodelatlng`
--
CREATE TABLE IF NOT EXISTS `postcodelatlng` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`postcode` varchar(8) NOT NULL,
`latitude` decimal(12,9) NOT NULL,
`longitude` decimal(12,9) NOT NULL,
PRIMARY KEY (`id`)
) AUTO_INCREMENT=1;
--
-- Indexes for table `postcodelatlng`
--
ALTER TABLE `postcodelatlng`
ADD PRIMARY KEY (`id`),
ADD KEY `postcode` (`postcode`),
ADD KEY `latitude` (`latitude`,`longitude`),
ADD KEY `longitude` (`longitude`,`latitude`) USING BTREE;
这里是数据示例:
INSERT INTO postcodelatitudelongitude (postcode,latitude,longitude) VALUES ('AB10', '57.13514','-2.11731');
INSERT INTO postcodelatitudelongitude (postcode,latitude,longitude) VALUES ('AB11', '57.13875','-2.09089');
INSERT INTO postcodelatitudelongitude (postcode,latitude,longitude) VALUES ('AB12', '57.10100','-2.11060');
INSERT INTO postcodelatitudelongitude (postcode,latitude,longitude) VALUES ('AB13', '57.10801','-2.23776');
dbfiddle https://www.db-fiddle.com/f/mi4D1937k9WpeM3ubMBLjw/0
【问题讨论】:
-
关于查询加速的问题很难回答,因为您没有提供查询绑定的数据。这可能是由于许可权的限制,但请理解,除非该场景可重现,否则您可能无法获得问题的适当答案。
-
数据在这里免费提供:freemaptools.com/download-uk-postcode-lat-lng.htmukpostcodesmysql.zip
-
我要做的就是优化查询
-
听起来不错,为什么不创建一个 dbfiddle 来证明您的问题呢?应该可以轻松链接它(至少)。 (如果您允许我发表评论,您想优化我所说的查询已经在问题中突出)
-
dbfiddle 会允许这种大小的数据库吗? 234MB