MySQL中行級(jí)鎖和表級(jí)鎖的區(qū)別小結(jié)
MySQL 中的行級(jí)鎖和表級(jí)鎖是兩種不同的鎖機(jī)制,它們?cè)诓l(fā)控制和鎖粒度方面有顯著的區(qū)別。了解這兩種鎖的區(qū)別及其使用場(chǎng)景,有助于優(yōu)化數(shù)據(jù)庫(kù)性能并確保數(shù)據(jù)一致性。以下是對(duì)行級(jí)鎖和表級(jí)鎖的詳細(xì)解析,并結(jié)合代碼示例來(lái)幫助理解。
一、行級(jí)鎖 vs 表級(jí)鎖
1. 行級(jí)鎖(Row-level Locks)
- 粒度:行級(jí)鎖鎖定的是表中的單個(gè)行。
- 并發(fā)性:行級(jí)鎖具有較高的并發(fā)性能,因?yàn)椴煌聞?wù)可以并發(fā)地修改不同的行。
- 開(kāi)銷(xiāo):管理行級(jí)鎖的開(kāi)銷(xiāo)較高,因?yàn)樾枰櫭恳恍械逆i狀態(tài)。
- 使用場(chǎng)景:適用于需要高并發(fā)讀寫(xiě)操作的場(chǎng)景。
2. 表級(jí)鎖(Table-level Locks)
- 粒度:表級(jí)鎖鎖定的是整個(gè)表。
- 并發(fā)性:表級(jí)鎖的并發(fā)性能較低,因?yàn)橐粋€(gè)事務(wù)鎖定整個(gè)表后,其他事務(wù)不能同時(shí)對(duì)該表進(jìn)行任何讀寫(xiě)操作。
- 開(kāi)銷(xiāo):管理表級(jí)鎖的開(kāi)銷(xiāo)較低,相對(duì)于行級(jí)鎖而言更簡(jiǎn)單。
- 使用場(chǎng)景:適用于讀多寫(xiě)少的場(chǎng)景,如報(bào)表查詢(xún)等。
二、InnoDB 中的行級(jí)鎖
InnoDB 存儲(chǔ)引擎支持行級(jí)鎖,這使得它適用于高并發(fā)的事務(wù)處理。
1. 共享鎖(S-lock)
多個(gè)事務(wù)可以同時(shí)讀取同一行,但不能修改。
START TRANSACTION; -- 獲取共享鎖 SELECT * FROM employees WHERE id = 1 LOCK IN SHARE MODE; -- 完成事務(wù) COMMIT;
2. 排它鎖(X-lock)
一個(gè)事務(wù)獲取排它鎖后,其他事務(wù)不能讀取或修改該行。
START TRANSACTION; -- 獲取排它鎖 SELECT * FROM employees WHERE id = 1 FOR UPDATE; -- 完成事務(wù) COMMIT;
三、MyISAM 中的表級(jí)鎖
MyISAM 存儲(chǔ)引擎只支持表級(jí)鎖。
1. 讀鎖(共享鎖)
多個(gè)客戶(hù)端可以同時(shí)讀取表,但不能寫(xiě)入。
LOCK TABLES employees READ; -- 在鎖定的表上執(zhí)行讀操作 SELECT * FROM employees; -- 釋放鎖 UNLOCK TABLES;
2. 寫(xiě)鎖(排它鎖)
一個(gè)客戶(hù)端獲取寫(xiě)鎖后,其他客戶(hù)端不能讀取或?qū)懭朐摫怼?/p>
LOCK TABLES employees WRITE;
-- 在鎖定的表上執(zhí)行寫(xiě)操作
INSERT INTO employees (name, department_id) VALUES ('Alice', 1);
-- 釋放鎖
UNLOCK TABLES;
四、使用示例
1. 行級(jí)鎖示例
假設(shè)有一個(gè) employees 表,我們使用 InnoDB 存儲(chǔ)引擎,并展示行級(jí)鎖的使用。
CREATE TABLE employees (
id INT AUTO_INCREMENT PRIMARY KEY,
name VARCHAR(255) NOT NULL,
department_id INT NOT NULL,
created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP
) ENGINE=InnoDB;
INSERT INTO employees (name, department_id) VALUES ('Alice', 1), ('Bob', 2);
兩會(huì)話并發(fā)更新不同的行:
- 會(huì)話 1
START TRANSACTION; UPDATE employees SET name = 'Charlie' WHERE id = 1; -- 保持事務(wù)未提交
- 會(huì)話 2
START TRANSACTION; UPDATE employees SET name = 'Dave' WHERE id = 2; -- 保持事務(wù)未提交
這種情況下,兩會(huì)話可以并發(fā)執(zhí)行,因?yàn)樗鼈冃薷牡氖遣煌男小?/p>
2. 表級(jí)鎖示例
假設(shè)有一個(gè) employees 表,我們使用 MyISAM 存儲(chǔ)引擎,并展示表級(jí)鎖的使用。
CREATE TABLE employees (
id INT AUTO_INCREMENT PRIMARY KEY,
name VARCHAR(255) NOT NULL,
department_id INT NOT NULL,
created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP
) ENGINE=MyISAM;
INSERT INTO employees (name, department_id) VALUES ('Alice', 1), ('Bob', 2);
兩會(huì)話并發(fā)更新表:
- 會(huì)話 1
LOCK TABLES employees WRITE; UPDATE employees SET name = 'Charlie' WHERE id = 1; -- 保持鎖未釋放
- 會(huì)話 2
-- 會(huì)被阻塞,直到會(huì)話 1 釋放鎖 LOCK TABLES employees WRITE; UPDATE employees SET name = 'Dave' WHERE id = 2;
這種情況下,會(huì)話 2 會(huì)被阻塞,直到會(huì)話 1 釋放鎖,因?yàn)?MyISAM 使用的是表級(jí)鎖。
五、意向鎖
InnoDB 還支持意向鎖(Intent Locks),這是表級(jí)鎖和行級(jí)鎖之間的一種協(xié)調(diào)機(jī)制。意向鎖分為意向共享鎖(IS)和意向排它鎖(IX)。
- 意向共享鎖(IS-lock):事務(wù)打算在某些行上加共享鎖時(shí),先在表級(jí)加意向共享鎖。
- 意向排它鎖(IX-lock):事務(wù)打算在某些行上加排它鎖時(shí),先在表級(jí)加意向排它鎖。
意向鎖是由 InnoDB 自動(dòng)管理的,不需要顯式加鎖。
六、總結(jié)
行級(jí)鎖和表級(jí)鎖是 MySQL 中兩種重要的鎖機(jī)制,它們?cè)阪i粒度和并發(fā)控制方面有顯著的區(qū)別:
- 行級(jí)鎖:粒度較小,適合高并發(fā)讀寫(xiě)操作,但管理開(kāi)銷(xiāo)較高。InnoDB 存儲(chǔ)引擎支持行級(jí)鎖。
- 表級(jí)鎖:粒度較大,適合讀多寫(xiě)少的場(chǎng)景,管理開(kāi)銷(xiāo)較低。MyISAM 存儲(chǔ)引擎使用表級(jí)鎖。
通過(guò)合理選擇和使用鎖機(jī)制,可以有效提高數(shù)據(jù)庫(kù)的并發(fā)性能和數(shù)據(jù)一致性。理解和掌握這些鎖機(jī)制的細(xì)節(jié),有助于在設(shè)計(jì)和優(yōu)化數(shù)據(jù)庫(kù)時(shí)做出更好的決策。
到此這篇關(guān)于MySQL中行級(jí)鎖和表級(jí)鎖的區(qū)別小結(jié)的文章就介紹到這了,更多相關(guān)MySQL 行級(jí)鎖和表級(jí)鎖內(nèi)容請(qǐng)搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!
相關(guān)文章
MySQL Binlog 日志監(jiān)聽(tīng)與 Spring 集成實(shí)戰(zhàn)場(chǎng)景
MySQL 的二進(jìn)制日志(binlog)有三種常見(jiàn)的格式:Statement 模式、Row 模式和Mixed 模式,這篇文章主要介紹了MySQL Binlog 日志監(jiān)聽(tīng)與 Spring 集成實(shí)戰(zhàn),需要的朋友可以參考下2024-12-12
給MySQL表中的字段設(shè)置默認(rèn)值的兩種方法
在MySQL中,我們可以為表的字段設(shè)置默認(rèn)值,以確保在插入新記錄時(shí),如果沒(méi)有為該字段指定值,將使用默認(rèn)值,要為MySQL表中的字段設(shè)置默認(rèn)值,我們可以在創(chuàng)建表時(shí)或者在已存在的表上使用ALTER TABLE語(yǔ)句進(jìn)行修改,下面將展示兩種設(shè)置默認(rèn)值的方法,需要的朋友可以參考下2023-11-11
MySql如何實(shí)現(xiàn)遠(yuǎn)程登錄MySql數(shù)據(jù)庫(kù)過(guò)程解析

