PostgreSQL查询优化器--逻辑查询优化--视图优化(一)
来源:互联网 发布:linux 中文输入法安装 编辑:程序博客网 时间:2024/06/07 15:46
8.1.1 视图重写
PostgreSQL有一个模块,称为规则模块,用以处理规则。规则系统把查询修改为需要考虑规则的形式,然后把修改过的查询传递给查询优化器执行。视图被作为规则的子部分,在此被处理。所以,PostgreSQL通过规则模块(pg_rewrite_query函数)支持逻辑查询优化的视图重写,也就是把视图用视图的定义替代,视图定义在SQL中相当于子查询。PostgreSQL统一对子查询进行优化。
PostgreSQL支持简单视图重写和复杂视图的重写,支持对带有简单视图重写后的SQL语句进行优化,但
支持对带有复杂视图重写后的SQL语句做优化。下面我们通过四组针对视图的查询实例进行对比,以帮助读者掌握PostgreSQL对视图重写的支持情况。
首先让我们做一些准备性的工作。
创建表,命令如下:
CREATE TABLE t1 (a1 int UNIQUE, b1 int);
CREATE TABLE t2 (a2 int UNIQUE, b2 int);
CREATE TABLE t3 (a3 int UNIQUE, b3 int);
创建简单视图,命令如下:
CREATE VIEW v_t_1_2 AS SELECT * FROM t1, t2;
创建复杂视图,命令如下:
CREATE VIEW v_t_gd_1_2 AS SELECT DISTINCT t1.b1, t2.b2 FROM t1, t2 GROUP BY t1.b1, t2.b2;
示例1 在简单视图上执行连接操作。
直接用视图和表做连接操作,查询执行计划如下:
test=# EXPLAIN SELECT * FROM t1, v_t_1_2 WHERE t1.a1<20;
QUERY PLAN
------------------------------------------------------------------
Nested Loop (cost=0.00..250291.15 rows=20000000 width=24)
-> Nested Loop (cost=0.00..273.65 rows=20000 width=16) //两个t1连接后才与t2连接
-> Seq Scan on t1 (cost=0.00..15.00 rows=1000 width=8) //视图中的t1顺序扫描
-> Materialize (cost=0.00..8.70 rows=20 width=8) //FROM子句中的t1索引扫描后物化
-> Index Scan using t1_a1_key on t1 (cost=0.00..8.60 rows=20 width=8)
Index Cond: (a1 < 20)
-> Materialize (cost=0.00..20.00 rows=1000 width=8)
-> Seq Scan on t2 (cost=0.00..15.00 rows=1000 width=8)
(8 行记录)
从查询执行计划看,视图v_t_1_2的名称没有出现,而且视图中的t1表和原先的t1表先进行连接,t2表被最后连接,这说明视图被重写,重写后的视图定义部分作为子查询被上拉处理,上拉后的查询语句已经只是三个表(t1、t1、t2)之间进行连接了。
另外,对于条件“a1 < 20”,只在一个t1表被索引扫描时被使用,没有能在t1表被顺序扫描时使用,且t1表被扫描2次,不能有效利用物化的结果,PostgreSQL对于这种情况有待改进。
等价于上一条视图的子查询,没有视图存在,查询执行计划如下:
test=# EXPLAIN SELECT * FROM t1, (SELECT * FROM t1, t2) t12 WHERE t1.a1<20;
QUERY PLAN
------------------------------------------------------------------
Nested Loop (cost=0.00..250291.15 rows=20000000 width=24)
-> Nested Loop (cost=0.00..273.65 rows=20000 width=16)
-> Seq Scan on t1 (cost=0.00..15.00 rows=1000 width=8)
-> Materialize (cost=0.00..8.70 rows=20 width=8)
-> Index Scan using t1_a1_key on t1 (cost=0.00..8.60 rows=20 width=8)
Index Cond: (a1 < 20)
-> Materialize (cost=0.00..20.00 rows=1000 width=8)
-> Seq Scan on t2 (cost=0.00..15.00 rows=1000 width=8)
(8 行记录)
从查询执行计划看,本条子查询语句的查询执行计划与上一条基于视图的查询语句的查询执行计划完全相同,这表明二者是完全等价的,PostgreSQL支持对简单视图的重写。
- PostgreSQL查询优化器--逻辑查询优化--视图优化(一)
- PostgreSQL查询优化器--逻辑查询优化--视图优化(一)
- PostgreSQL查询优化器--逻辑查询优化--视图优化(二)
- PostgreSQL查询优化器--逻辑查询优化--视图优化(三)
- PostgreSQL查询优化器--逻辑查询优化--子查询优化(一)
- PostgreSQL查询优化器--逻辑查询优化--子查询优化(二)
- PostgreSQL查询优化器--逻辑查询优化--子查询优化(三)
- MySQL查询优化器--逻辑查询优化技术(一)--视图重写
- PostgreSQL查询优化器--逻辑优化功能篇--目录
- MySQL查询优化器--逻辑查询优化技术(五)--外连接的消除(一)
- PostgreSQL查询优化:查询条件优化一(条件分类)
- PostgreSQL查询优化简介
- PostgreSQL的查询优化
- MySQL查询优化器--逻辑查询优化技术(二)--子查询优化(二)
- MySQL查询优化器--逻辑查询优化技术(二)--子查询优化(三)
- MySQL查询优化器--逻辑查询优化技术(二)--子查询优化(四)
- MySQL查询优化器--逻辑查询优化技术(二)--子查询优化
- SQL优化--逻辑优化--子查询优化(MySQL)
- MySQL查询优化器--非SPJ优化(三)--DISTINCT优化
- Python 错误类型及解决方法
- MySQL查询优化器--非SPJ的优化
- MySQL查询优化器--非SPJ优化(四)--LIMIT优化
- 进程创建时线程栈处理
- PostgreSQL查询优化器--逻辑查询优化--视图优化(一)
- PostgreSQL查询优化器--逻辑查询优化--视图优化(二)
- 数据库使用经验---面对大数据背景
- PostgreSQL查询优化器--逻辑查询优化--视图优化(三)
- 开源数据库的编译---MySQL的编译(For MySQL V5.6.12)
- Spring EL表示式的运用@Value
- PostgreSQL查询优化器--逻辑查询优化--子查询优化(一)
- 迎接2014---跨年礼物送给各位朋友
- PostgreSQL查询优化器--逻辑查询优化--子查询优化(二)