对PostgreSQL的 seq scan , bitmap index scan 和 index scan 的进一步理解

本文涉及的产品
云原生数据库 PolarDB MySQL 版,通用型 2核4GB 50GB
云原生数据库 PolarDB PostgreSQL 版,标准版 2核4GB 50GB
简介:

开始

参考momjian 的文章:

http://momjian.us/main/writings/pgsql/optimizer.pdf

首先,构造一个数据分布明显倾斜的表(有的值占据了70%以上的分布)

复制代码
postgres=# CREATE TEMPORARY TABLE sample (letter, junk) AS
postgres-# SELECT substring(relname, 1, 1), repeat('x', 250)
postgres-# FROM pg_class
postgres-# ORDER BY random();
SELECT 291
postgres=# 


postgres=# CREATE INDEX i_sample on sample (letter);
CREATE INDEX
postgres=# 
postgres
=# CREATE OR REPLACE FUNCTION lookup_letter(text) RETURNS SETOF text AS $$ postgres$# BEGIN postgres$# RETURN QUERY EXECUTE' postgres$# EXPLAIN SELECT letter postgres$# FROM sample postgres$# WHERE letter ='''||$1||''''; postgres$# END postgres$# $$ LANGUAGE plpgsql; CREATE FUNCTION postgres=# postgres=# WITH letters (letter, count) AS ( postgres(# SELECT letter, COUNT(*) postgres(# FROM sample postgres(# GROUP BY 1 postgres(# ) postgres-# SELECT letter, count, (count * 100.0 / (SUM(count) OVER ()))::numeric(4,1) AS "%" postgres-# FROM letters postgres-# ORDER BY 2 DESC; letter | count | % --------+-------+------ p | 223 | 76.6 c | 12 | 4.1 s | 9 | 3.1 r | 8 | 2.7 f | 6 | 2.1 d | 5 | 1.7 u | 5 | 1.7 _ | 5 | 1.7 t | 5 | 1.7 v | 4 | 1.4 e | 3 | 1.0 a | 3 | 1.0 i | 2 | 0.7 k | 1 | 0.3 (14 rows) postgres=#
复制代码

此时,如果不通过 analyze 来更新统计信息,得到的 执行计划是不准确的。所以先要更新统计信息:

postgres=#analyze sampel;

postgres=#

然后,再来看执行的情况:

[作者:技术者高健@博客园  mail: luckyjackgao@gmail.com ]

复制代码
postgres=# EXPLAIN SELECT *     FROM sample
WHERE letter ='p';
                        QUERY PLAN                         
-----------------------------------------------------------
 Seq Scan on sample  (cost=0.00..14.64 rows=223 width=256)
   Filter: (letter = 'p'::text)
(2 rows)

postgres=# 

postgres=# EXPLAIN SELECT *
FROM sample
WHERE letter = 'd';
                              QUERY PLAN                               
-----------------------------------------------------------------------
 Bitmap Heap Scan on sample  (cost=4.29..14.24 rows=5 width=256)
   Recheck Cond: (letter = 'd'::text)
   ->  Bitmap Index Scan on i_sample  (cost=0.00..4.29 rows=5 width=0)
         Index Cond: (letter = 'd'::text)
(4 rows)
postgres=# 

postgres=# EXPLAIN SELECT *
FROM sample
WHERE letter = 'k';
                               QUERY PLAN                                
-------------------------------------------------------------------------
 Index Scan using i_sample on sample  (cost=0.00..8.27 rows=1 width=256)
   Index Cond: (letter = 'k'::text)
(2 rows)
postgres=# 
复制代码

数据分布很大(比如70%以上),用index scan 已经没有意义了,因为数据太多了。所以就不如用 全表扫描了。

数据分布较小(比如 1.7%),则用 bitmap index scan。数据更少的时候,用的是 index scan。

需要引起注意的是, bitmap index 也可以用在where 条件单一的时候。

结束




本文转自健哥的数据花园博客园博客,原文链接:http://www.cnblogs.com/gaojian/archive/2012/11/09/2761952.html,如需转载请自行联系原作者

相关实践学习
使用PolarDB和ECS搭建门户网站
本场景主要介绍基于PolarDB和ECS实现搭建门户网站。
阿里云数据库产品家族及特性
阿里云智能数据库产品团队一直致力于不断健全产品体系,提升产品性能,打磨产品功能,从而帮助客户实现更加极致的弹性能力、具备更强的扩展能力、并利用云设施进一步降低企业成本。以云原生+分布式为核心技术抓手,打造以自研的在线事务型(OLTP)数据库Polar DB和在线分析型(OLAP)数据库Analytic DB为代表的新一代企业级云原生数据库产品体系, 结合NoSQL数据库、数据库生态工具、云原生智能化数据库管控平台,为阿里巴巴经济体以及各个行业的企业客户和开发者提供从公共云到混合云再到私有云的完整解决方案,提供基于云基础设施进行数据从处理、到存储、再到计算与分析的一体化解决方案。本节课带你了解阿里云数据库产品家族及特性。
目录
相关文章
|
4月前
|
关系型数据库 MySQL 测试技术
MySQL 报错 ERROR 1709: Index column size too large
MySQL 报错 ERROR 1709: Index column size too large
212 4
|
5月前
|
缓存 关系型数据库 MySQL
MySQL数据库——InnoDB引擎-架构-内存结构(Buffer Pool、Change Buffer、Adaptive Hash Index、Log Buffer)
MySQL数据库——InnoDB引擎-架构-内存结构(Buffer Pool、Change Buffer、Adaptive Hash Index、Log Buffer)
98 3
|
6月前
|
存储 关系型数据库 MySQL
MySQL的优化利器⭐️Multi Range Read与Covering Index是如何优化回表的?
本文以小白的视角使用通俗易懂的流程图深入浅出分析Multi Range Read与Covering Index是如何优化回表
|
6月前
|
SQL 关系型数据库 MySQL
mysql查询语句的访问方法const、ref、ref_or_null、range、index、all
mysql查询语句的访问方法const、ref、ref_or_null、range、index、all
|
6月前
|
关系型数据库 MySQL 索引
mysql中force index强制索引
mysql中force index强制索引
56 0
|
存储 SQL 缓存
一文带你了解MySQL之Adaptive Hash Index
在InnoDB体系架构图的内存结构中,还有一块区域名为:Adaptive Hash Index,翻译成中文:自适应哈希索引,缩写:AHI,它是一个纯内存结构,我们今天就来了解它。
1458 0
|
6月前
|
关系型数据库 MySQL
mysql 5.5.62版本建表语句报错: Index column size too large. The maximum column size is 767 bytes
mysql 5.5.62版本建表语句报错: Index column size too large. The maximum column size is 767 bytes
226 0
|
6月前
|
关系型数据库 MySQL
MySQL【问题 02】报错 1709 - Index column size too large. The maximum column size is 767 bytes. 可能是最简单的方法
MySQL【问题 02】报错 1709 - Index column size too large. The maximum column size is 767 bytes. 可能是最简单的方法
213 0
|
关系型数据库 MySQL 数据库
Mysql中key与index区别
Mysql中key与index区别
|
存储 SQL 关系型数据库
MySQL 优化 index merge(索引合并)引起的死锁分析(强烈推荐)
生产环境出现死锁流水,通过查看死锁日志,看到造成死锁的是两条一样的update语句(只有where条件中的值不同),如下:

热门文章

最新文章