我有一张带有自动增量主键的表。此表用于存储数百万条记录,我现在不需要删除任何内容。问题是,当插入新行时,由于某些错误,自动增量键在自动增量ID中留下一些空隙。例如,在5之后,下一个id为8,留下6和7的间隙结果是,当我计算行数时,结果为28000,但最大ID为58000.可能是什么原因?我没有删除任何东西。我该如何解决这个问题。
P.S。我在插入记录时使用insert ignore,以便在我尝试在唯一列中插入重复条目时不会出错。
答案 0 :(得分:12)
这是设计上的,并且将永远发生。
为什么?
让我们做两个正在进行INSERT的重叠事务
然后
如果保证连续值,则每个交易必须一个接一个地发生。不太可扩展。
另见Do Inserted Records Always Receive Contiguous Identity Values(SQL Server但适用相同的原则)
答案 1 :(得分:3)
您可以创建一个触发器来处理自动增量:
CREATE DEFINER=`root`@`localhost` TRIGGER `mytable_before_insert` BEFORE INSERT ON `mytable` FOR EACH ROW
BEGIN
SET NEW.id = (SELECT IFNULL(MAX(id), 0) + 1 FROM mytable);;
END
答案 2 :(得分:2)
这是mySQL的存储引擎InnoDB中的一个问题。
确实不是问题
检查文档时 http://dev.mysql.com/doc/refman/5.0/en/innodb-auto-increment-handling.html
它基本上说InnoDB使用特殊的表来启动时自动增量
它使用的查询类似于
SELECT MAX(ai_col) FROM t FOR UPDATE;
这样可以提高并发性,而不会对数据产生任何影响。
没有使用MyISAM而不是InnoDB作为存储引擎
答案 3 :(得分:1)
也许(我没有对此进行测试)解决方案是将innodb_autoinc_lock_mode
设置为0
。
根据{{3}},这可能会使事情变得更慢(如果在单个查询中执行多行插入),但应该删除间隙。
答案 4 :(得分:1)
您可以尝试插入:
insert ignore into table select (select max(id)+1 from table), "value1", "value2" ;
这将尝试