mysql - 插入查询优化

标签 mysql sql group-by

我有一个包含 ~2M 行的表。它在 (id,round) 上有 B 树主键,还有 2 个其他(似乎不相关的)索引。

我的问题是:

insert into a1
select * from cars
where (id, round) in (select id, min(round) from cars group by id)

上面的查询需要大约 30 秒才能运行 但是为什么下面的查询

insert into a1
select * from cars
where (id, round) in (select id, max(round) from cars group by id)

似乎要花很长时间才能运行?我等了几个小时。我唯一改变的是 min->max

PS:这是创建表

CREATE TABLE `cars` (
  `id` int(11) NOT NULL,
  `make` varchar(128) NOT NULL,
  `miles` varchar(128) NOT NULL,
  `time` timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP,
  `round` int(11) NOT NULL,
  `location` varchar(50) DEFAULT NULL,
  PRIMARY KEY (`id`,`round`),
  KEY `time` (`time`),
  KEY `make` (`make`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1

最佳答案

IN 当前 MySQL 查询优化器未以最佳方式优化子查询。

我会使用:

INSERT INTO a1
  SELECT c.* 
  FROM 
        cars AS c
    JOIN 
        ( SELECT id, MAX(round) AS round
          FROM cars 
          GROUP BY id
        ) AS m
      ON  (m.id, m.round) = (c.id, c.round) 

您在 (id, round) 上已有的索引将使子查询运行得非常快并且只运行一次(作为派生表)。另一种方式,使用 IN,子查询对 cars 表的每一行运行一次(这就是它很慢的原因)。使用 EXPLAIN 检查执行计划。

关于mysql - 插入查询优化,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/9356489/

相关文章:

mysql - SQL 选择消除在下一列中有 2 个其他值的重复值

c# - Linq 选择新对象

mySQL 用修剪删除 char(13)

php - 如何防止在SQL中插入现有数据

Mysql 检查时间之间的可用性

mysql - 如何使用 SQL 仅选择每个组中最新的一个?

sql - 进程无法在 'sp_replcmds' 上执行 'database_name'

ruby-on-rails - 按唯一值分组,同时求和/添加其他值

php - 大型 MySQL 查询和插入

MySQL 选择查询