Skip to content

Latest commit

 

History

History
111 lines (70 loc) · 3.43 KB

20210916_01.md

File metadata and controls

111 lines (70 loc) · 3.43 KB

鞭尸系列(DB错误使用姿势)-1 用count判断是否存在

作者

digoal

日期

2021-09-16

标签

PostgreSQL , 错误使用姿势 , 是否存在


背景

1、业务诉求

判断记录是否存在?

2、错误姿势例子

count >=1 判断是否存在

select count(*) into vv from tbl where xxx;  
  
if vv >= 1 then  
...  

3、原理以及会导致什么问题

count会执行聚合操作, 如果符合条件的记录较多, 非常浪费IO和CPU. 如果是高频查询, 可以在TOP SQL中看到这类SQL.

《PostgreSQL 如何查找TOP SQL (例如IO消耗最高的SQL) (包含SQL优化内容) - 珍藏级 - 数据库慢、卡死、连接爆增、慢查询多、OOM、crash、in recovery、崩溃等怎么办?怎么优化?怎么诊断?》

4、正确姿势例子

1、函数中使用

  
perfrom 1 from tbl where xxx limit 1;  
if found then  
...  
end if;  

2、SQL中使用

select 1 from tbl where xxx limit 1;  

3、如果是数据的merge需求(有就更新、没有就插入)建议的用法

insert into tbl values () on conflict do update set c1=excluded.c1 ...;   

5、前后对比

例子:

平均每个gid 100条记录

create unlogged table tbl (id int, gid int, info text, crt_time timestamp);  
insert into tbl select generate_series (1,1000000), random()*10000, md5(random()::text), clock_timestamp();  
create index idx_tbl_1 on tbl (gid);  

50%存在, 50%不存在判断

vi bad.sql  
\set gid random(1,20000)   
select count(*) from tbl where gid=:gid;  
  
vi good.sql  
\set gid random(1,20000)  
select 1 from tbl where gid=:gid limit 1;  

结果

pgbench -M prepared -n -r -P 1 -f ./bad.sql -c 16 -j 16 -T 60  
qps: 66965  
  
pgbench -M prepared -n -r -P 1 -f ./good.sql -c 16 -j 16 -T 60  
qps: 108034  

您的愿望将传达给PG kernel hacker、数据库厂商等, 帮助提高数据库产品质量和功能, 说不定下一个PG版本就有您提出的功能点. 针对非常好的提议,奖励限量版PG文化衫、纪念品、贴纸、PG热门书籍等,奖品丰富,快来许愿。开不开森.

digoal's wechat