Mysql自增主键id不是以此逐级递增的处理
Mysql自增主键id不是以此逐级递增
一、介绍
在mysql数据库添加数据时使用ON DUPLICATE KEY UPDATE进行数据更新时可能会出现id不是逐级以此递增的,而是间断递增。
如id从10下次添加可能就是15或者其他的数字,两个数字之间间隔是ON DUPLICATE KEY UPDATE执行的次数,也就是说ON DUPLICATE KEY UPDATE在执行更新的时候把该表主键进行自增加一。
如图所示
二、问题介绍
在对于同一个表进行新增和修改时我用了两个mapper接口方法,也就是说使用了两次ON DUPLICATE KEY UPDATE操作,这样就会导致该表主键在你更新的时候就进行自增了。等到下次insert时就会出现不是逐级递增了。
三、解决方法
将数据库的insert和update进行拆分。
自增主键的优缺点
自增主键
这种方式是使用数据库提供的自增数值型字段作为自增主键,它的优点是:
(1)数据库自动编号,速度快,而且是增量增长,按顺序存放,对于检索非常有利;
(2)数字型,占用空间小,易排序,在程序中传递也方便;
(3)如果通过非系统增加记录时,可以不用指定该字段,不用担心主键重复问题。
其实它的缺点也就是来自其优点,缺点如下:
(1)因为自动增长,在手动要插入指定ID的记录时会显得麻烦,尤其是当系统与其它系统集成时,需要数据导入时,很难保证原系统的ID不发生主键冲突(前提是老系统也是数字型的)。特别是在新系统上线时,新旧系统并行存在,并且是异库异构的数据库的情况下,需要双向同步时,自增主键将是你的噩梦;
(2)在系统集成或割接时,如果新旧系统主键不同是数字型就会导致修改主键数据类型,这也会导致其它有外键关联的表的修改,后果同样很严重;
(3)若系统也是数字型的,在导入时,为了区分新老数据,可能想在老数据主键前统一加一个字符标识(例如“o”,old)来表示这是老数据,那么自动增长的数字型又面临一个挑战。
以上为个人经验,希望能给大家一个参考,也希望大家多多支持我们。
相关推荐
-
MySQL表自增id溢出的故障复盘解决
问题:MySQL某个表自增id溢出导致某业务block 背景: tokudb引擎的一个大表tb1,存放业务上的机审日志,每天有大量的写入, 并且由于历史原因,这张表是int signed 类型的,最大只能存 2147483647行记录 . 处理过程: 增加DBLE中间件代理,然后做range分区,将新数据写到新加的的一个分片上. 同时业务上修改连接将这个表tb1的连接方式改走DBLE. 但是业务上改完代码后,发现还有残余的部分insert into tb1的写请求被转发到了老的表上,且有些表被错
-
mysql id从1开始自增 快速解决id不连续的问题
mysql id从1开始自增 解决id不连续 作为一个强迫症患者,对于表格内某些行删除之后,id不连续这个问题完全无法容忍,一开始使用 TRUNCATE TABLE tablename 来实现id从头自增,但是这个命令同时也会清空整个表,真的是坑爹啊. 后面才发现了正确的做法: alter table tablename auto_increment = 1; 这个命令不会改动现有的表的内容和顺序,同时新插入行的id会先使用已删除的id,完美填补空缺id. mysql自增id跳跃解决(不删除数据
-
详解mysql插入数据后返回自增ID的七种方法
引言 mysql 和 oracle 插入的时候有一个很大的区别是: oracle 支持序列做 id: mysql 本身有一个列可以做自增长字段. mysql 在插入一条数据后,如何能获得到这个自增 id 的值呢? 一:使用 last_insert_id() SELECT LAST_INSERT_ID(); 1. 每次 mysql 的 query 操作在 mysql 服务器上可以理解为一次"原子"操作, 写操作常常需要锁表, 这里的锁表是 mysql 应用服务器锁表不是我们的应用程序锁表
-
Mysql join联表及id自增实例解析
join的写法 如果用left join 左边的表一定是驱动表吗?两个表的join包含多个条件的等值匹配,都要写道on还是只把一个写到on,其余写道where部分? create table a(f1 int, f2 int, index(f1))engine=innodb; create table b(f1 int, f2 int)engine=innodb; insert into a values(1,1),(2,2),(3,3),(4,4),(5,5),(6,6); insert in
-
关于mysql自增id,你需要知道的
导读:在使用MySQL建表时,我们通常会创建一个自增字段(AUTO_INCREMENT),并以此字段作为主键.本篇文章将以问答的形式讲述关于自增id的一切. 注: 本文所讲的都是基于Innodb存储引擎. 1.MySQL为什么建议将自增列id设为主键? 如果我们定义了主键(PRIMARY KEY),那么InnoDB会选择主键作为聚集索引.如果没有显式定义主键,则InnoDB会选择第一个不包含有NULL值的唯一索引作为主键索引.如果也没有这样的唯一索引,则InnoDB会选择内置6字节长的ROWID
-
Mysql主键UUID和自增主键的区别及优劣分析
引言 之前有段时间用postgresql 数据库,在上云之后,从自增主键变为uuid,感觉uuid全球唯一,很方便. 最近用mysql,发现mysql主键都是选择自增主键,仔细比较一下,为什么mysql选择自增主键,有什么不同. 在mysql5.0之前,如果是多个master复制的环境,无法用自增主键,因为可能重复.在5.0以及之后的版本通过配置自增偏移量解决了整个问题. 什么情况下我们希望用uuid 1. 避免重复,便于scale,这就是我们做cloud service的时候选择uuid的主要
-
MySQL的自增ID(主键) 用完了的解决方法
在 MySQL 中用很多类型的自增 ID,每个自增 ID 都设置了初始值.一般情况下初始值都是从 0 开始,然后按照一定的步长增加(一般是自增 1).一般情况下,我们都是用int(11)来作为数据表的自增 ID,在 MySQL 中只要定义了这个数的字节长度,那么就会有上限. MySQL的自增ID(主键) 用完了,怎么办? 如果用 int unsigned (int,4个字节 ), 我们可以算下最大当前声明的自增ID最大是多少,由于这里定义的是 int unsigned,所以最大可以达到2的32幂
-
关于MySQL自增ID的一些小问题总结
下面这几个小问题都是基于 InnoDB 存储引擎的. 1. ID最大的记录删除后,新插入的记录ID是什么 例如当前表中有ID为1,2,3三条记录,把3删除,新插入记录的ID从哪儿开始? 答案: 从4开始. 实验 创建表 tb0,ID自增: create table tb0(id int unsigned auto_increment primary key); 插入3条记录: insert into tb0 values(null); 删除ID为3的记录: delete from tb0 whe
-
Mysql自增主键id不是以此逐级递增的处理
Mysql自增主键id不是以此逐级递增 一.介绍 在mysql数据库添加数据时使用ON DUPLICATE KEY UPDATE进行数据更新时可能会出现id不是逐级以此递增的,而是间断递增. 如id从10下次添加可能就是15或者其他的数字,两个数字之间间隔是ON DUPLICATE KEY UPDATE执行的次数,也就是说ON DUPLICATE KEY UPDATE在执行更新的时候把该表主键进行自增加一. 如图所示 二.问题介绍 在对于同一个表进行新增和修改时我用了两个mapper接口方法,也
-
Mysql更新自增主键id遇到的问题
目录 为什么要更新自增id 问题 如何解决 本是一个自己知道的问题,还是差点踩坑(差点忘了,还好上线前整理上线点时想起来了),特此记录下来 为什么要更新自增id 我是因为历史业务上的坑,导致必须更新一批id,且为了避免冲突需要将id扩大多少倍进行更新,因为我这个表的数据数量不高,属于高读低写的情况,所以就简单的扩大了1000 问题 MySQL中如果我们把自增主键更新为更大的值(例如现在自增id最大值是1000,你更新id=49这个记录到id=1049),MySQL并不会把表的自增值修改为更新后的
-
面试官问订单ID是如何生成的?难道不是MySQL自增主键
一个美女面试官坐到我的对面,发光logo的MacBook也挡不住她那圆润可爱的脸庞. 程序媛本就稀有,美女面试官更是难寻. 这么温柔可爱的面试官,应该不会为难我吧.嗯,应该是的,毕竟我这么帅气,面试可能就是走个过场.美女面试官是不是单身?毕竟程序员都不善交流,因为我也是单身,难道我的姻缘就在此注定.孩子的名字我都想好了.一冰!好名字. 面试官: 小伙子,你低着头笑什么呐.开始面试了,你知道订单ID是怎么生成的吗? 啥?订单ID怎么生成?美女怎么不按套路出牌!HashMap实现原理,我已经倒背如流
-
使用prometheus统计MySQL自增主键的剩余可用百分比
最近生产环境一套数据库因为疯狂写日志数据,造成主键值溢出的情况出现,因此有必要将这个指标监控起来. mysqld_exporter自带的这个功能,下面是我使用的启动参数: nohup ./mysqld_exporter --config.my-cnf="./my.cnf" --web.listen-address=":9104" --collect.heartbeat --collect.auto_increment.columns --collect.binlog
-
详解MySQL自增主键的实现
目录 一.自增值保存在哪儿? 二.自增值修改机制 三.自增值的修改时机 四.自增锁的优化 五.自增主键用完了 一.自增值保存在哪儿? 不同的引擎对于自增值的保存策略不同 1.MyISAM引擎的自增值保存在数据文件中 2.InnoDB引擎的自增值,在MySQL5.7及之前的版本,自增值保存在内存里,并没有持久化.每次重启后,第一次打开表的时候,都会去找自增值的最大值max(id),然后将max(id)+步长作为这个表当前的自增值 select max(ai_col) from table_name
-
为什么mysql自增主键不是连续的
目录 一 前言 二 自增值存储说明 三 自增值修改机制 四 自增值修改时机 五 导致自增值不连续的原因 5.1 唯一键冲突 5.2 事务回滚 5.3 批量写库操作 六 参考文档 一 前言 提出这个问题,是因为在工作中发现 mysql 中的 user 表的 id 默认是自增的,但是数据库存储的结果却不是连续的. user 表结构: CREATE TABLE `user` ( `id` bigint(20) unsigned NOT NULL AUTO_INCREMENT COMMENT '递增id
-
详解mybatis插入数据后返回自增主键ID的问题
1.场景介绍: 开发过程中我们经常性的会用到许多的中间表,用于数据之间的对应和关联.这个时候我们关联最多的就是ID,我们在一张表中插入数据后级联增加到关联表中.我们熟知的mybatis在插入数据后返回的是插入成功的条数,那么这个时候我们想要得到相应的这条新增数据的ID,该怎么办呢? 2.插入数据返回自增主键ID方法(一) 在映射器中配置获取记录主键值xml映射: 在xml中定义useGeneratedKeys为true,返回主键id的值,keyProperty和keyColumn分别代表数据库
-
浅谈MySQL中的自增主键用完了怎么办
在面试中,大家应该经历过如下场景 面试官:"用过mysql吧,你们是用自增主键还是UUID?" 你:"用的是自增主键" 面试官:"为什么是自增主键?" 你:"因为采用自增主键,数据在物理结构上是顺序存储,性能最好,blabla-" 面试官:"那自增主键达到最大值了,用完了怎么办?" 你:"what,没复习啊!!" (然后,你就可以回去等通知了!) 这个问题是一个粉丝给我提的,我觉得
-
深入谈谈MySQL中的自增主键
MySQL的主键可以是自增的,那么如果在断电重启后新增的值还会延续断电前的自增值吗?自增值默认为1,那么可不可以改变呢?下面就说一下 MySQL的自增值. 特点 保存策略 1.如果存储引擎是 MyISAM,那么这个自增值是存储在数据文件中的: 2.如果是 InnoDB引擎,1)在 5.6之前是存储在内存中,没有持久化,在重启后会去找最大的键值,举个例子,如果一个表当前数据行里最大 id是10,AUTO_INCREMENT=11.这时候,我们删除 id=10 的行,AUTO_INCREMENT 还
-
Mybatis-Plus默认主键策略导致自动生成19位长度主键id的坑
某天检查一位离职同事写的代码,发现其对应表虽然设置了AUTO_INCREMENT自增,但页面新增功能生成的数据主键id很诡异,长度达到了19位,且不是从1开始递增的-- 我检查了一下,发现该表目前自增主键已经变成从1468844351843872770开始递增了-- 这就很奇怪了,目前该表数据量很少,且主键是设置AUTO_INCREMENT,正常而言,应该自增id仍在1000范围内,但目前已经变成一串长数字. 底层ORM框架用的是Mybatis-Plus,我寻思了一下,这看起来像是在插入数据库就
随机推荐
- 使用SQL查询DB2 9中的XML数据
- 有关DOM元素与事件的3个谜题
- Linux中split大文件分割和cat合并文件详解
- C#多线程学习之(四)使用线程池进行多线程的自动管理
- Oracle 细粒度审计(FGA)初步认识
- c#开发的程序安装时动态指定windows服务名称
- Ubuntu中搭建Nodejs开发环境过程分享
- DIV和CSS排版中制作细线条的方法小结
- jQuery实现鼠标滑向当前图片高亮显示并且其它图片变灰的方法
- 基于Java HashMap的死循环的启示详解
- php中rename函数用法分析
- 浅析php适配器模式(Adapter)
- Android自定义View实现支付宝支付成功-极速get花式Path炫酷动画
- java基于jedisLock—redis分布式锁实现示例代码
- Windows 64 位 mysql 5.7以上版本包解压中没有data目录和my-default.ini及服务无法启动的快速解决办法(问题小结)
- JS实现li标签的删除
- Python OpenCV中的resize()函数的使用
- flutter ExpansionTile 层级菜单的实现
- 使用TransitionDrawable实现多张图片淡入淡出效果
- Go 语言的指针的学习笔记