http://dev.mysql.com/doc/refman/5.6/en/innodb-auto-increment-handling.htmlhtml
MySQL/InnoDB處理AUTO_INCREMENT(一)mysql
AUTO_INCREMENT Handling in InnoDBsql
下面所使用的表數據庫
CREATE TABLE people ( person_id BIGINT NOT NULL AUTO_INCREMENT, first_name VARCHAR(20), last_name VARCHAR(20), PRIMARY KEY (person_id) );
auto-increment counter的初始化據個人分析存在於三個節點:服務器
數據庫服務器啓動後表的第一次插入前less
經過show table status命令查詢表的狀態信息,若是auto-increment counter沒有初始化,就要在show table status以前初始化。性能
表新建後,要初始化auto-increment counter。ui
下面是mysql官方文檔的描述:http://dev.mysql.com/doc/refman/5.6/en/innodb-auto-increment-traditional.htmlthis
If you specify an AUTO_INCREMENT column for an InnoDB table, the table handle in the InnoDB data dictionary contains a special counter called the auto-increment counter that is used in assigning new values for the column. This counter is stored only in main memory, not on disk.spa
InnoDB uses the following algorithm to initialize the auto-increment counter for a table t that contains an AUTO_INCREMENT column named ai_col: After a server startup(在服務器啓動後,counter的值因爲存在內存中,會消失), for the first insert into a table t(對於第一次插入), InnoDB executes the equivalent(等價的,等效的) of this statement:
SELECT MAX(ai_col) FROM t FOR UPDATE;
InnoDB increments the value retrieved(取回,恢復) by the statement and assigns it to the column and to the auto-increment counter for the table. By default, the value is incremented by one(默認的這個值會增長one). This default can be overridden by the auto_increment_increment configuration setting.
If the table is empty, InnoDB uses the value 1. This default can be overridden by the auto_increment_offset configuration setting.
If a SHOW TABLE STATUS statement examines(調查) the table t before the auto-increment counter is initialized, InnoDB initializes but does not increment the value and stores it for use by later inserts. This initialization uses a normal exclusive-locking read on the table and the lock lasts to the end of the transaction.
以下所示,經過truncate將一張表初始化,經過show table status能夠看到Auto_increment爲1,這只是存儲到counter中以供下次插入使用的。這個初始化過程會加一個排它鎖把表鎖住,這個鎖會一直持續到事務結束。
mysql> truncate people; Query OK, 0 rows affected (0.54 sec) mysql> show table status from local_database like 'people'\G *************************** 1. row *************************** Name: people Engine: InnoDB Version: 10 Row_format: Compact Rows: 0 Avg_row_length: 0 Data_length: 16384 Max_data_length: 0 Index_length: 0 Data_free: 0 Auto_increment: 1 Create_time: 2014-11-04 15:36:51 Update_time: NULL Check_time: NULL Collation: latin1_swedish_ci Checksum: NULL Create_options: Comment: 1 row in set (0.00 sec) mysql> select max(person_id) from people; +----------------+ | max(person_id) | +----------------+ | NULL | +----------------+ 1 row in set (0.00 sec)
InnoDB follows the same procedure(相同的過程) for initializing the auto-increment counter for a freshly created table(初始化新創建的表的auto-increment counter).
最重要的一個概念:table-level AUTO-INC lock,做用就是當執行一個insert語句時,這個鎖會把表鎖住,知道這個insert語句執行完成,而後表解鎖,而不是等到這個事務結束。
When accessing the auto-increment counter, InnoDB uses a special table-level AUTO-INC lock that it keeps to the end of the current SQL statement, not to the end of the transaction. The special lock release strategy was introduced to improve concurrency for inserts into a table containing an AUTO_INCREMENT column. Nevertheless(然而,儘管如此), two transactions cannot have the AUTO-INC lock on the same table simultaneously(同時,一塊兒,一齊), which can have a performance(性能) impact(影響) if the AUTO-INC lock is held for a long time. That might be the case for a statement such as INSERT INTO t1 ... SELECT ... FROM t2 that inserts all rows from one table into another.
auto_increment_increment:自增值的自增量
auto_increment_offset: 自增值的偏移量
設置了兩個值以後,改服務器的自增字段值限定爲:
auto_increment_offset + auto_increment_increment*N 的值,其中N>=0,可是上限仍是要受定義字段的類型限制。
好比:
auto_increment_offset=1
auto_increment_increment=2
那麼ID則是全部的奇數[1,3,5,7,.....]
若是:
auto_increment_offset=5
auto_increment_increment=10
那麼ID則是全部的奇數[5,15,25,35,.....]
============END============