`
wzhiju
  • 浏览: 141358 次
  • 性别: Icon_minigender_1
  • 来自: 北京
社区版块
存档分类
最新评论

mysql 数据库自增id 的总结

阅读更多

mysql数据库使用auto_increment 字段来辅助为自增列赋值。

 

SHOW VARIABLES LIKE 'auto_incre%';

 

 输出

 

auto_increment_increment 1
auto_increment_offset 1

 

auto_increment_increment  = 1 ,每次插入数据,id++;auto_increment_offset =1 ,说明从1开始。

一般情况下auto_increment_increment=1,auto_increment_offset=1.是默认初始值。

我们可以在my.cnf文件中进行重新指定。auto_increment满足一个数学当纳法推导公

式:

value=auto_increment_increment*N+auto_increment_offset

 

表中有auto_increment列,innodb用一种锁策略来保正这个auto_increment列值。

如果我们创建一个表,指定了auto_increment表。那么innodb会维护一个auto_increment

计数器。

 

当访问这个计数器,innodb会使用表级锁来锁定这访问过程,这个发生在分析auto_increment

值的过程中,而不是在一个执行事务中。也就是说:这个访问发生在事务执行前面。所以和这个锁

不是发生整个事务过程中,仅仅是分析语句判断出auto_increment这一过程中.

 

auto_increment计数器,一直维护在内存中,当server重启或是停止后重启,innodb会为每个表

初始化这个计数器.

 

 


对一个含有自增列(通常为id)的表执行

 

mysql> SHOW CREATE TABLE table_name;

 

 可以得到类似输出:

 

CREATE TABLE `news` (
`id` bigint(20) NOT NULL AUTO_INCREMENT,
`title` varchar(255) NOT NULL,
`url` varchar(255) NOT NULL,
`pub_date` datetime NOT NULL,
`site` tinyint(4) NOT NULL,
`created_at` datetime NOT NULL,
`updated_at` datetime DEFAULT NULL,
`org` varchar(255) DEFAULT NULL,
`author` varchar(255) DEFAULT NULL,
`trend` tinyint(4) DEFAULT '-1',
`md5url` char(32) NOT NULL,
`content` longtext NOT NULL,
PRIMARY KEY (`id`),
UNIQUE KEY `md5url` (`md5url`),
KEY `pub_date` (`pub_date`),
KEY `created_at` (`created_at`),
KEY `title` (`title`)
) ENGINE=InnoDB AUTO_INCREMENT=704677 DEFAULT CHARSET=utf8

 

 

其中该状态下,表中AUTO_INCREMENT 字段值为704677 ,说明下一个插入的id 为704677 ,同时插入成功后,AUTO_INCREMENT=704678.

 

mysql 数据库中的id设为自增,容易产生id不连续的问题。有时将一个表中的所有数据清除,但是在插入数据时,id还是在未清除前的基础上累加。

要解决的问题:

1. 删除数据,同时要求再次插入数据时,id从1 开始累计

(1) TRUNCATE TABLE table_name;

(2) DELETE FROM table_name;    

 ALTER TABLE table_name auto_increment =1 ;

对上面两种方法进行一下分析。Truncate table 表名 速度快,而且效率高,因为:TRUNCATE TABLE 在功能上与不带 WHERE 子句的 DELETE 语句相同:二者均删除表中的全部行。但 TRUNCATE TABLE 比 DELETE 速度快,且使用的系统和事务日志资源少。DELETE 语句每次删除一行,并在事务日志中为所删除的每行记录一项。TRUNCATE TABLE 通过释放存储表数据所用的数据页来删除数据,并且只在事务日志中记录页的释放。

  TRUNCATE TABLE 删除表中的所有行,但表结构及其列、约束、索引等保持不变。新行标识所用的计数值重置为该列的种子。如果想保留标识计数值,请改用 DELETE。如果要删除表定义及其数据,请使用 DROP TABLE 语句。

2. 查看当前状态下一个表的auto_increment 值:

 

SHOW TABLE STATUS LIKE 'table_name'

输出:

Name: ddx
Engine: InnoDB
Version: 10
Row_format: Compact
Rows: 2449
Avg_row_length: 93
Data_length: 229376
Max_data_length: 0
Index_length: 114688
Data_free: 0
Auto_increment: 2353
Create_time: 2012-05-02 12:54:55
Update_time: NULL
Check_time: NULL
Collation: utf8_general_ci
Checksum: NULL
Create_options:
Comment:

  可以查看该表当前的Auto_increment的值。

 

3. 对有些失败插入操作,如果不是语法错误,比如重复的唯一键值,也会造成自增id的不连续。

4. 5.1.22之前,innodb使用一个表锁解决自增字段的一致性问题(内部是用一个计数器维护,每次自增时要加表锁),如果一行一行的插入数据则没有什么问题,但是如果大量的并发插入就废了,表锁会引起SQL堵塞,不但影响效率,而且可能会瞬间达到max_connections而崩溃。在 5.1.22之后,innodb使用新的方式解决自增字段一致性问题,对于可以预判行数的insert语句,innodb使用一个轻量级的互斥量。如:某一insert语句1执行前,表的AUTO_INCREMENT=1,语句1的插入行数已知为3,innodb在语句1的实际插入操作执行前就预分配给该语句三个自增值,当有一个新的insert语句2要执行时,读取的AUTO_INCREMENT=4,这样虽然语句1可能还没有执行完,语句2就可直接执行无需等待语句2。这种方式对于可预判插入行数的插入语句有效,如:insert和replace。对于无法提前获知插入行数的语句,如:insert...select...、replace...select...和load

data则innodb还是使用表锁。

insert语句中有时会显示的设置自增字段的值,对于这种情况innodb还是会预分配给语句总行数的自增值而不是只有实际使用系统自增的行。因而有可能会造成自增字段的值不连续。如:

 

INSERT INTO t1 (c1,c2) VALUES (1,'a'), (NULL,'b'), (5,'c'), (NULL,'d');

 c1 为自增字段,实际的AUTO_INCREMENT 会大2。

设置新自增互斥方式:通过配置选项:innodb_autoinc_lock_mode,它是专门用来在使用auto_increment的情况下调整锁策略的,目前有三种选择:
innodb_autoinc_lock_mode = 0 (“traditional” lock mode:全部使用表锁)
innodb_autoinc_lock_mode = 1 (默认)(“consecutive” lock
mode:可预判行数时使用新方式,不可时使用表锁) 
innodb_autoinc_lock_mode = 2 (“interleaved” lock
mode:全部使用新方式,不安全,不适合replication)

分享到:
评论

相关推荐

    mysql 数据库自增id 的总结.docx

    在MySQL数据库中,自增ID(Auto Increment)是一种常见的特性,用于在插入新记录时自动为指定列(通常是主键)生成唯一的递增数值。在标题提到的文档中,主要讨论了如何使用自增ID以及与之相关的INSERT和REPLACE语句...

    mysql自增字段重排 mysql删除表后自增字段从1开始.pdf

    在MySQL数据库中,自增字段(AUTO_INCREMENT)是一种常见的特性,用于在插入新记录时自动为该字段生成唯一的序列编号。这个字段通常用于主键,确保每个记录的唯一性。以下是对MySQL自增字段相关知识点的详细说明: ...

    MySQL的自增ID(主键) 用完了的解决方法

    MySQL的自增ID(主键) 用完了,怎么办? 如果用 int unsigned (int,4个字节 ), 我们可以算下最大当前声明的自增ID最大是多少,由于这里定义的是 int unsigned,所以最大可以达到2的32幂次方 – 1 = 4294967295。 ...

    MySQL8自增主键变化.doc

    MySQL 官网解释自增 ID 冲突问题是因为在 MySQL5.7 中,对于自增主键的分配规则是由 InnoDB 数据字典内部一个计数器来决定的,而该计数器维护在了内存中,并不会持久化到磁盘中,此时硬盘中并无数据,当数据库重启的...

    mysql自增ID起始值修改方法

    在mysql中很多朋友都认为字段为AUTO_INCREMENT类型自增ID值是无法修改,其实这样理解是错误的,下面介绍mysql自增ID的起始值修改与设置方法。通常的设置自增字段的方法:创建表格时添加: 代码如下:create table ...

    MySQL分表自增ID问题的解决方法

    然而,当进行分表后,传统的自增ID策略会遇到问题,因为MySQL的自动增量特性不适用于跨表的唯一标识生成。本篇文章将探讨如何解决MySQL分表自增ID的问题。 首先,我们了解MySQL自增ID的工作原理。MySQL的自增ID特性...

    关于MySQL自增ID的一些小问题总结

    总结来说,理解MySQL自增ID的工作原理对于数据库设计和管理至关重要。在规划数据库时,应考虑可能的数据增长,并选择适当的数据类型来确保ID的可用性。在进行大量插入和删除操作时,尤其需要注意ID的管理和自增值的...

    常用数据库的自增字段创建方法汇总

    总结来说,不同数据库系统中自增字段的创建方式有所不同,但都遵循一定的逻辑规则。开发者需要根据所使用的数据库系统选择合适的创建方式。以上介绍的方法涵盖了大部分常用的数据库系统,希望对开发者有所帮助。

    两种mysql对自增id重新从1排序的方法

    MySQL 数据库在处理自增(Auto Increment)ID 时,常常会遇到需要重置自增序列的情况,例如在数据初始化、测试环境复原或者数据清理之后。本文将介绍两种方法来实现 MySQL 自增 ID 从 1 开始重新排序。 方法一:...

    java快速ID自增器

    总结来说,"Java快速ID自增器"是一种解决在Java应用中生成唯一自增ID的策略。它可以是基于Java内置的原子类、数据库序列、分布式ID生成算法,或者是结合数据库和Spring框架的高级应用场景。选择哪种方案取决于具体的...

    Go-beego框架自增id自写方法

    在大多数数据库系统中,自增ID是由数据库管理系统自动管理的,每次插入新记录时,它会自动递增并赋值给主键字段。然而,Beego ORM在执行批量插入时,并不返回这些生成的ID。 解决这个问题,我们可以分为以下几个...

    mysql如何让自增id归0解决方案

    在MySQL数据库中,自增ID(AUTO_INCREMENT)是一种常见的用于主键字段的特性,它会自动为新插入的行提供唯一的标识符,每次插入新行时递增。然而,在某些场景下,例如数据库初始化或者数据清理后,我们可能需要让...

    Java获取最后插入MySQL记录的自增ID值的3种方法

    在Java编程中,当我们在MySQL数据库中执行插入操作并希望获取新插入记录的自增ID时,有多种方法可以实现这一需求。以下是三种常见的方法,适用于不同的场景。 **方法一:使用PreparedStatement的RETURN_GENERATED_...

    MySQL数据库设计、优化.pptx

    MySQL数据库设计与优化是数据库管理中的重要环节,它关乎到系统的性能、稳定性和可扩展性。本讲座由叶金荣分享,主要涵盖了多个关键方面,包括规范、基础规范、命名规范、库表规范、字段规范、索引规范以及开发环境...

    php 根据自增id创建唯一编号类

    在PHP编程中,有时我们需要为数据记录生成唯一的标识符,特别是在数据库操作中,自增ID是一种常见的做法。但是,为了满足特定需求,如增加可读性或者安全性,我们可能需要进一步定制这个标识符。本篇文章将详细介绍...

    MySQL自增ID耗尽实例讲解

    总的来说,了解和正确管理MySQL的自增ID、row_id、XID和trx_id是保证数据库可靠性和可用性的重要方面。在设计和使用MySQL时,应当注意自增ID类型的选择,以及合理设置初始值,防止ID耗尽。同时,理解事务处理机制,...

Global site tag (gtag.js) - Google Analytics