新聞中心
mysql 中如何給已存在的表中字段增設(shè)置主鍵?
1、打開navicat工具,連接上mysql服務(wù)器,選擇完數(shù)據(jù)庫之后,選擇一個(gè)表右擊選擇設(shè)計(jì)表(這里為了演示測(cè)試,隨便選擇一個(gè)表即可)。
為梓潼等地區(qū)用戶提供了全套網(wǎng)頁設(shè)計(jì)制作服務(wù),及梓潼網(wǎng)站建設(shè)行業(yè)解決方案。主營業(yè)務(wù)為網(wǎng)站設(shè)計(jì)、網(wǎng)站制作、梓潼網(wǎng)站設(shè)計(jì),以傳統(tǒng)方式定制建設(shè)網(wǎng)站,并提供域名空間備案等一條龍服務(wù),秉承以專業(yè)、用心的態(tài)度為用戶提供真誠的服務(wù)。我們深信只要達(dá)到每一位用戶的要求,就會(huì)得到認(rèn)可,從而選擇與我們長(zhǎng)期合作。這樣,我們也可以走得更遠(yuǎn)!
2、在設(shè)計(jì)表頁面,可以看到當(dāng)前表的所有字段信息,我們選擇的學(xué)生表有一個(gè)id字段,目前該表沒有主鍵字段。
3、如圖,在最后一列右擊選擇主鍵,即可將該字段設(shè)置為主鍵,也可以直接點(diǎn)擊鼠標(biāo)左鍵,可以快速添加和取消主鍵。
4、設(shè)置完主鍵之后,可以看到一把鎖的標(biāo)志,并且有一個(gè)1字,因?yàn)橐粋€(gè)表可以給多個(gè)字段添加主鍵,則為聯(lián)合主鍵,這樣就顯示為主鍵1,主鍵2等。
5、主鍵設(shè)置完成之后,還沒有自增,選擇id字段之后,在下方,如圖,勾選自動(dòng)遞增,這樣id在每次插入記錄之后都會(huì)自增一個(gè)值。
6、設(shè)置完成主鍵和自增之后,點(diǎn)擊保存,關(guān)閉當(dāng)前窗口,然后選擇表名右擊選擇對(duì)象信息。
7、在DLL頁面中,可以看到剛剛添加的主鍵和自增的DLL語句,這里就是創(chuàng)建表的DLL語句。
8、上面有提到聯(lián)合主鍵,其實(shí)一個(gè)表可以給多個(gè)字段設(shè)置主鍵,這樣可以組成聯(lián)合主鍵,對(duì)于特定的業(yè)務(wù),聯(lián)合主鍵也是必須的。
技術(shù)分享 | 關(guān)于 MySQL 自增 ID 的事兒
當(dāng)我們使用 MySQL 進(jìn)行數(shù)據(jù)存儲(chǔ)時(shí),一般會(huì)為一張表設(shè)置一個(gè)自增主鍵,當(dāng)有數(shù)據(jù)行插入時(shí),該主鍵字段則會(huì)根據(jù)步長(zhǎng)與偏移量增長(zhǎng)(默認(rèn)每次+1)。
下文以 Innodb 引擎為主進(jìn)行介紹,使用自增主鍵的好處有很多,如:索引空間占比小、范圍查詢與排序都友好、避免像 UUID 這樣隨機(jī)字符串帶來的頁分裂問題等...
當(dāng)我們對(duì)該表設(shè)置了自增主鍵之后,則會(huì)在該表上產(chǎn)生一個(gè)計(jì)數(shù)器,用于為自增列分配 ID 。
自增的值并不是保存在表結(jié)構(gòu)信息內(nèi)的,對(duì)于不同的版本它們有如下的區(qū)別:
計(jì)數(shù)器的值存儲(chǔ)在內(nèi)存中的,重啟后丟棄,下一次將讀取最大的一個(gè)自增ID往后繼續(xù)發(fā)號(hào)。
計(jì)數(shù)器的值將會(huì)持久化到磁盤。在每次發(fā)號(hào)時(shí)都將寫入 Redolog ,并在每個(gè) Checkpoint 都進(jìn)行保存,重啟時(shí)候使用 Redolog 恢復(fù)重啟之前的值。
可以預(yù)先確定插入行數(shù)的語句(像簡(jiǎn)單 insert 的語句包含多個(gè) value 這種情況也是屬于簡(jiǎn)單插入,因?yàn)樵谶M(jìn)行插入時(shí)就已經(jīng)可以確定行數(shù)了)
預(yù)先不知道要插入的行數(shù)的語句(包括 INSERT ... SELECT, REPLACE ... SELECT 和 LOAD DATA 語句,但不包括 plain INSERT )
如果一個(gè)事務(wù)正在向表中插入值,則會(huì)產(chǎn)生表級(jí)的共享鎖,以便當(dāng)前事務(wù)插入的行接收連續(xù)的主鍵值。
當(dāng)處于[ 傳統(tǒng)模式 ]與[ 連續(xù)模式 ]時(shí),每次訪問計(jì)數(shù)器時(shí)都會(huì)加上一個(gè)名為 AUTO-INC 的表級(jí)鎖
傳統(tǒng)模式:鎖只持有到該語句執(zhí)行結(jié)束,注意是語句結(jié)束,不是事務(wù)結(jié)束
連續(xù)模式:批量插入時(shí)鎖持有到該語句執(zhí)行結(jié)束,簡(jiǎn)單插入時(shí)鎖持有到申請(qǐng)完自增ID后即釋放,不直到語句完成
通過調(diào)整 innodb_autoinc_lock_mode 配置項(xiàng),可以定義 AUTO-INC 鎖的模式,不同的模式對(duì)應(yīng)的策略與鎖的粒度也將不同。
當(dāng)使用基于 Binlog 的復(fù)制場(chǎng)景時(shí),對(duì)于 statement(SBR)同步模式下只有[ 傳統(tǒng)模式 ]與[ 連續(xù)模式 ]能保證語句的正確性。
基于 row(RBR)行復(fù)制的情況下任何配置模式都可以。
執(zhí)行語句時(shí)加 AUTO-INC 表級(jí)鎖,執(zhí)行完畢后釋放
針對(duì) Bulk Inserts 時(shí)才會(huì)采用 AUTO-INC 鎖,而針對(duì) Simple Inserts 時(shí),則采用了一種新的輕量級(jí)的互斥鎖來分配 auto_increment 列的值。
該模式下可以保證同一條 insert 語句中新插入的自增 ID 都是連續(xù)的,但如果前一個(gè)事務(wù) rollback 丟棄了一部分 ID 的話也會(huì)存在后續(xù) ID 出現(xiàn)間隔的情況。
來一個(gè)分配一個(gè),不會(huì)產(chǎn)生 AUTO-INC 表級(jí)鎖 ,僅僅會(huì)鎖住分配 ID 的過程。
由于鎖的粒度減少,多條語句在插入時(shí)進(jìn)行鎖競(jìng)爭(zhēng),自增長(zhǎng)的值可能不是連續(xù)的。
且當(dāng) Binlog 模式為 statement(SBR)時(shí)自增 ID 不能保證數(shù)據(jù)的正確性
不一定,業(yè)務(wù)也不應(yīng)該過分依賴 MySQL 自增 ID 的連續(xù)性,在以下三種情況下,并不能保證自增 ID 的連續(xù)性:
假設(shè)已存在數(shù)據(jù){1,張三},且張三所屬的字段設(shè)置了唯一主鍵
此時(shí)再次插入{null,張三}時(shí)候,主鍵沖突插入失敗,但表的計(jì)數(shù)器已由2變成了3
當(dāng)下次插入{null,李四}的時(shí)候最終入庫的會(huì)變成{3,李四}
在一個(gè)事務(wù)里進(jìn)行數(shù)據(jù)的插入,但最后并沒提交,而是執(zhí)行了 Rollback 。那么計(jì)數(shù)器已遞增的 ID 是不會(huì)返還的,而是被直接丟棄。
發(fā)生大量插入時(shí)可能會(huì)出現(xiàn)自增 ID 并不是連續(xù)的情況
當(dāng)我們?yōu)楸碓O(shè)置了自增主鍵后,自增 ID 的范圍則與主鍵的數(shù)據(jù)類型長(zhǎng)度相關(guān)。
如果沒有一張表里沒有設(shè)置任何主鍵,則會(huì)自動(dòng)生成一個(gè)隱性的6字節(jié)的 row_id 作為主鍵,它的取值范圍為 0 到 2^48-1。
row_id 是由一個(gè)全局的 dict_sys.row_id 參數(shù)進(jìn)行維護(hù)的,所有沒有主鍵的表都會(huì)用上它(并不是每一個(gè)表單獨(dú)占一份 row_id list )
那么針對(duì)這兩種主鍵,則會(huì)有以下兩種情況發(fā)生:
當(dāng)自增 ID 到達(dá)上限后,受到主鍵數(shù)據(jù)類型的影響,計(jì)數(shù)器發(fā)放的下一個(gè) ID 也是當(dāng)前這個(gè) Max ID ,當(dāng)執(zhí)行語句時(shí)則會(huì)提示主鍵沖突。
建議根據(jù)業(yè)務(wù)合理規(guī)劃,在進(jìn)行表設(shè)計(jì)時(shí)就選擇適合的數(shù)據(jù)類型。
當(dāng)然也可以直接選擇 Bigint 類型,它的取值范圍是無符號(hào)情況下:0到 2^64–1(18446744073709551615)
這里并不是指 bigint 類型一定不會(huì)用完,畢竟一個(gè)有范圍的持續(xù)增長(zhǎng)的值一定會(huì)有溢出的時(shí)候,只是說一般場(chǎng)景下它都是足夠使用的。
當(dāng) row_id 使用完后則又會(huì)從 0 開始發(fā)放,此時(shí)新插入的數(shù)據(jù)將覆蓋回 row_id=0 的數(shù)據(jù)行。
由于它并不產(chǎn)生錯(cuò)誤,還會(huì)造成數(shù)據(jù)的覆蓋寫。所以我們平時(shí)還是盡量給表都設(shè)置一個(gè)合理的主鍵才是。
在實(shí)際業(yè)務(wù)場(chǎng)景中,ID 常常需要返回給客戶端用來進(jìn)行相關(guān)業(yè)務(wù)操作。
假如我們有個(gè) userinfo?uid=? 的 API 接口,而用戶 ID 是自增的,這時(shí)會(huì)發(fā)生什么?
該接口通過簡(jiǎn)單的嘗試就可以暴露出真實(shí)的業(yè)務(wù)用戶總數(shù),可以很方便的使用爬蟲從1開始遞增獲取數(shù)據(jù)信息。
那么有的同學(xué)說,我既想使用自增 ID 帶來的好處,也不想承受這種比較常見的問題,那該怎么辦呢?
在輸出或者獲取前對(duì)指定字段進(jìn)行可逆的轉(zhuǎn)義操作
優(yōu)點(diǎn):實(shí)現(xiàn)起來比較簡(jiǎn)單,無論單體業(yè)務(wù)或者分布式應(yīng)用都無需考慮對(duì)數(shù)據(jù)源的解析,只需在客戶端實(shí)現(xiàn)自己的轉(zhuǎn)義與解析方法即可;
缺點(diǎn):業(yè)務(wù)入侵較大,且需要前后端各個(gè)合作方確認(rèn)統(tǒng)一的標(biāo)準(zhǔn);如果轉(zhuǎn)義方法有調(diào)整,變更影響面也會(huì)很大;字符串長(zhǎng)度會(huì)隨ID長(zhǎng)度而變化,使用空位填充也會(huì)特別明顯;
優(yōu)點(diǎn):由于采用了時(shí)間戳進(jìn)行 ID 生成,該 ID 是有序的,對(duì)范圍查詢與排序都比較友好;
缺點(diǎn):需要保證發(fā)號(hào)節(jié)點(diǎn)的高可用性;另外由于生成時(shí)依賴時(shí)間戳,需要考慮時(shí)鐘回?fù)芘c時(shí)鐘同步的問題;
維護(hù)一份 ID 與 hash 的映射字典,它可以存在于客戶端本身,也可以依賴其他如 Redis 、ETCD 之類的組件
優(yōu)點(diǎn):hash 長(zhǎng)度不會(huì)隨著 ID 長(zhǎng)度或值的變化而變化;可以根據(jù)已有的 hash code 來造布隆過濾器;
缺點(diǎn):業(yè)務(wù)入侵較大,查詢時(shí)同樣需要先根據(jù) hash key 找到對(duì)應(yīng)的 ID 值;需要考慮選擇合適的 hash 算法以及解決 hash 沖突或擴(kuò)容的問題。
mysql創(chuàng)建數(shù)據(jù)庫時(shí)怎么將主鍵設(shè)置為UUID,建表語句怎么寫
mysql設(shè)置UUID為主鍵需要先將數(shù)據(jù)類型設(shè)置為VARCHAR(36),然后插入數(shù)據(jù)的時(shí)候用UUID函數(shù)插入U(xiǎn)UID。下面我用win10系統(tǒng)下的CMD命令行具體演示一下:
1、打開CMD,輸入mysql -uroot -p命令連接mysql,如下圖所示
2、通過create創(chuàng)建表,指定ID為varchar(36),并設(shè)置為主鍵,如下圖所示
3、在插入數(shù)據(jù)的時(shí)候,調(diào)用uuid()函數(shù)往主鍵字段里插入uuid值,如下圖所示
4、最后查詢插入的數(shù)據(jù)就可以看到id主鍵列存放的是uuid類型了,如下圖所示
如何設(shè)置mysql 自動(dòng)插入id
設(shè)置mysql?自動(dòng)插入id,需要設(shè)置id為整形自動(dòng)增長(zhǎng)的主鍵。下面介紹設(shè)置方法,
通過一個(gè)例子說明:
創(chuàng)建一張表student
create?table?student(
id?int(5)?not?null?auto_increatment,
name?varchar(20)?not?null,
age?int(3)?not?null,
primary?key(id));
在插入數(shù)據(jù)可以不用插入id,可以這樣:
insert?into?student(name,age)? values('xiaobai',12);第一條插入數(shù)據(jù)id默認(rèn)是1
insert?into?student?(name,age)?values('xiaoming',11);第二條插入數(shù)據(jù)id默認(rèn)是2,第三條,第四條,······,依次自動(dòng)增加。
由以上例子可知表插入數(shù)據(jù)的時(shí)候,無需插入id,即可自動(dòng)插入。
新聞標(biāo)題:mysql主鍵id怎么設(shè)計(jì)的 mysql主鍵的建立有幾種方法
本文URL:http://www.dlmjj.cn/article/dddgppj.html