mysql limit 分頁資料丟失問題測試
阿新 • • 發佈:2018-11-16
背景
前幾天看到有說mysql使用 limit 0,10 這種方式分頁會丟失資料,有人質疑說不會,動手驗證一下。
操作步驟
表結構如下:
create table `test`.`t_model`(
`id` bigint NOT NULL AUTO_INCREMENT COMMENT '自增主鍵',
`uid` bigint COMMENT '業務主鍵',
`modelid` varchar(50) COMMENT '字元主鍵',
`modelname` varchar(50) COMMENT '名稱',
`desc` varchar(50) COMMENT '描述' ,
primary key (`id`),
UNIQUE index `uid_unique` (`uid`),
key `modelid_index` (`modelid`) USING BTREE
) ENGINE=InnoDB charset=utf8 collate=utf8_bin;
構造測試資料語法如下:
drop procedure IF EXISTS u_head_and_low_pro;
delimiter $$
create procedure u_head_and_low_pro()
begin
DECLARE n int DEFAULT 1;
set @exesql = 'insert into t_model (uid,modelid,modelname,`desc`) values ';
set @exedata = '';
WHILE n < 10001 DO
set @exedata = concat(@exedata,"(",n,",","'id20170831",n,"','","name",n,"','","desc'",")");
if n % 1000 = 0
then
set @exesql = concat(@exesql,@exedata,";");
prepare stmt from @exesql;
execute stmt;
DEALLOCATE prepare stmt;
commit;
set @exesql = 'insert into t_model (uid,modelid,modelname,`desc`) values ';
set @exedata = "";
else
set @exedata = concat(@exedata,',');
end if;
set n = n + 1;
END WHILE;
end;$$
delimiter ;
查詢語法如下:
-- 第一頁
select * from t_model limit 0, 10;
-- 第二頁
select * from t_model limit 10, 10;
-- 第三頁
select * from t_model limit 20, 10;
-- 第四頁
select * from t_model limit 30, 10;
-- 第五頁
select * from t_model limit 40, 10;
在查詢時,第一頁是1~10,第二頁是11~20,第四頁時,查詢結果為:
id uid modelid modelname desc
31 31 id2017083131 name31 desc
32 32 id2017083132 name32 desc
33 33 id2017083133 name33 desc
34 34 id2017083134 name34 desc
35 35 id2017083135 name35 desc
36 36 id2017083136 name36 desc
37 37 id2017083137 name37 desc
38 38 id2017083138 name38 desc
39 39 id2017083139 name39 desc
40 40 id2017083140 name40 desc
此時,查詢第5頁應該是 41~50。如果某人A在介面上查詢資料,現在查詢到第4頁,在顯示完第4頁資料後,另外一個人B(或程式)將第11~20的資料刪除掉了,A再翻頁到第5頁時,此時資料為:
id uid modelid modelname desc
51 51 id2017083151 name51 desc
52 52 id2017083152 name52 desc
53 53 id2017083153 name53 desc
54 54 id2017083154 name54 desc
55 55 id2017083155 name55 desc
56 56 id2017083156 name56 desc
57 57 id2017083157 name57 desc
58 58 id2017083158 name58 desc
59 59 id2017083159 name59 desc
60 60 id2017083160 name60 desc
也就是說,A在本次操作過程中,如果一直往下翻頁到最後一頁的話,41~50 這頁的資料就無法看到,資料丟失了。
當然,如果重新整理一下介面,重新翻頁就沒有問題了。
結論
如果分頁查詢的表的資料插入和刪除等操作頻繁的話,建議還是使用 limit 10 這種語法方式分頁查詢,可以提升效能,也更準確。