文章點擊數、商品瀏覽數、廣告曝光數等計數器場景,典型特徵:極高寫入並發、讀多寫少、允許最終一致性。單行更新導致熱點鎖爭用,嚴重限制吞吐。
CREATE TABLE article (
id INT PRIMARY KEY,
title VARCHAR(200),
view_count BIGINT DEFAULT 0
);
-- UPDATE article SET view_count = view_count + 1 WHERE id = 123;
所有並發聚焦同一行 → 行鎖排隊 → 吞吐上限極低。
CREATE TABLE article_view (
article_id INT PRIMARY KEY,
view_count BIGINT DEFAULT 0
);
分離熱點欄位,但 UPDATE article_view SET view_count = view_count + 1 WHERE article_id = 123 仍是單行熱點,鎖爭用未解。
CREATE TABLE article_view (
article_id INT NOT NULL,
bucket TINYINT UNSIGNED NOT NULL COMMENT '分桶 0-99',
view_count BIGINT DEFAULT 0,
PRIMARY KEY (article_id, bucket)
) ENGINE=InnoDB;
bucket 0-99)bucket = FLOOR(RAND() * 100) 隨機選一桶更新SELECT SUM(view_count) FROM article_view WHERE article_id = 123
INSERT INTO article_view (article_id, bucket, view_count)
VALUES (123, FLOOR(RAND()*100), 1)
ON DUPLICATE KEY UPDATE view_count = view_count + 1;
無需應用層 SELECT 判斷,ON DUPLICATE KEY UPDATE 保證原子性。
| 桶數 | 寫入並發度 | 讀取聚合開銷 | 儲存空間 | 適用場景 |
|---|---|---|---|---|
| 10 | 低 | 極低 | 小 | 日 PV < 10萬 |
| 100 | 高 | 低 | 中 | 日 PV 10萬-1000萬(推薦起步) |
| 1000 | 極高 | 中 | 大 | 日 PV > 1000萬 |