插入增加自动增量值

时间:2017-06-14 16:02:20

标签: mysql

当我不想要它时,我的自动增量ID有问题。我知道在使用INSERT IGNORE时自动增量ID会增加,所以我正在解决这个问题,但仍然会得到一个我无法弄清楚的行为。

我正在构建一个规范化的事务表,在这个表中有一个名字列,它将有一个transaction_first_names的引用表。我的工作流程是将数据加载到非规范化的临时表中,将登台表中的值与参考表中的值进行比较,如果它们不存在于引用表中,则将数据从登台表移动到规范化表

我遇到的问题是,当我尝试插入任何" new"从临时表到参考表的值,它似乎以我无法解释的方式递增参考表中的自动增量id。我不会常常对自己的身份感到吝啬或吝啬,但作为一个持续的过程,我不想让身份不断被咀嚼。

这是我的设置,链接&码。正如您在第二个结果中看到的那样,最后插入的值的id为16,而目标是id应为9:

Runnable Example - http://rextester.com/KVMO89341

CREATE TABLE IF NOT EXISTS `transaction_first_names` (
    `id` INT(10) UNSIGNED NOT NULL AUTO_INCREMENT,
    `first_name` VARCHAR(100) NOT NULL,
    PRIMARY KEY (`id`),
    UNIQUE INDEX `u_first_name` (`first_name`)
)
COLLATE='utf8mb4_general_ci'
ENGINE=InnoDB;

CREATE TABLE IF NOT EXISTS `transaction_stage` (
    `transaction_id` BIGINT(20) UNSIGNED NOT NULL,
    `first_name` VARCHAR(255) NULL DEFAULT NULL,
    PRIMARY KEY (`transaction_id`),
    INDEX `first_name` (`first_name`(191))
)
COLLATE='utf8mb4_general_ci'
ENGINE=InnoDB;

TRUNCATE transaction_stage;
TRUNCATE transaction_first_names;

INSERT INTO `transaction_stage` (`transaction_id`, `first_name`) VALUES (3658822144, 'Michael');
INSERT INTO `transaction_stage` (`transaction_id`, `first_name`) VALUES (3658825319, 'Pete');
INSERT INTO `transaction_stage` (`transaction_id`, `first_name`) VALUES (3658828867, 'Robert');
INSERT INTO `transaction_stage` (`transaction_id`, `first_name`) VALUES (3658865656, 'Martin');
INSERT INTO `transaction_stage` (`transaction_id`, `first_name`) VALUES (3659080925, 'Charlews');
INSERT INTO `transaction_stage` (`transaction_id`, `first_name`) VALUES (3659943769, 'Christopher');
INSERT INTO `transaction_stage` (`transaction_id`, `first_name`) VALUES (3660191699, 'Robert');
INSERT INTO `transaction_stage` (`transaction_id`, `first_name`) VALUES (3660192662, 'Errol');
INSERT INTO `transaction_stage` (`transaction_id`, `first_name`) VALUES (3660194469, 'Frank');
INSERT INTO `transaction_stage` (`transaction_id`, `first_name`) VALUES (3660200483, 'Frank');

-- first select
SELECT DISTINCT st.first_name
FROM transaction_stage st
LEFT JOIN transaction_first_names f ON st.first_name <=> f.first_name
WHERE f.id IS NULL 
 AND st.first_name IS NOT NULL;

-- first insert
INSERT INTO transaction_first_names (`first_name`)
SELECT DISTINCT st.first_name
FROM transaction_stage st
LEFT JOIN transaction_first_names f ON st.first_name <=> f.first_name
WHERE f.id IS NULL 
 AND st.first_name IS NOT NULL;

-- second insert
INSERT INTO transaction_first_names (`first_name`)
VALUES ('Another name');

-- check autoincrement
SELECT * FROM transaction_first_names order by id asc;

DROP TABLE IF EXISTS transaction_first_names;
DROP TABLE IF EXISTS transaction_stage;

我尝试在第一个插入语句中包装select distinct,但没有运气。

1 个答案:

答案 0 :(得分:3)

啊,根据系统变量innodb_autoinc_lock_mode的设置方式,InnoDB的处理方式有所不同。

  

对于锁定模式1或2,连续语句之间可能会出现间隙   因为对于批量插入确切数量的自动增量值   每个声明所要求的内容可能不为人所知且过高估计   可能的。

https://dev.mysql.com/doc/refman/5.7/en/innodb-auto-increment-handling.html