mirror of
https://github.com/postgres/postgres.git
synced 2025-05-03 22:24:49 +03:00
Update optimizer readme.
This commit is contained in:
parent
390d5e9f14
commit
cd550c7672
@ -3,25 +3,24 @@ Summary
|
|||||||
|
|
||||||
The optimizer generates optimial query plans by doing several steps:
|
The optimizer generates optimial query plans by doing several steps:
|
||||||
|
|
||||||
1) Take each relation in a query, and make a RelOptInfo structure for it.
|
1) Take each relation in a query, and make a RelOptInfo structure for
|
||||||
Find each way of accessing the relation, called a Path, including
|
it. Find each way of accessing the relation, called a Path, including
|
||||||
sequential and index scans, and add it to the RelOptInfo.path_order
|
sequential and index scans, and add it to RelOptInfo.pathlist.
|
||||||
list.
|
|
||||||
|
|
||||||
2) Join each RelOptInfo to each other RelOptInfo as specified in the
|
2) Join each RelOptInfo to each other RelOptInfo as specified in the
|
||||||
WHERE clause. At this point each RelOptInfo is a single relation, so
|
WHERE clause. At this point each RelOptInfo is a single relation, so
|
||||||
you are joining every relation to every relation it is joined to in the
|
you are joining every relation to every relation as joined in the WHERE
|
||||||
WHERE clause.
|
clause.
|
||||||
|
|
||||||
Joins occur using two RelOptInfos. One is outer, the other inner.
|
Joins occur using two RelOptInfos. One is outer, the other inner.
|
||||||
Outers drive lookups of values in the inner. In a nested loop, lookups
|
Outers drive lookups of values in the inner. In a nested loop, lookups
|
||||||
of values in the inner occur by scanning to find each matching inner
|
of values in the inner occur by scanning to find each matching inner
|
||||||
row. In a mergejoin, inner rows are ordered, and are accessed in order,
|
row. In a mergejoin, inner and outer rows are ordered, and are accessed
|
||||||
so only one scan of inner is required to perform the entire join. In a
|
in order, so only one scan of inner is required to perform the entire
|
||||||
hashjoin, inner rows are hashed for lookups.
|
join. In a hashjoin, inner rows are hashed for lookups.
|
||||||
|
|
||||||
Each unique join combination becomes a new RelOptInfo. The RelOptInfo
|
Each unique join combination becomes a new RelOptInfo. The RelOptInfo
|
||||||
is now the joining of two relations. RelOptInfo.path_order are various
|
is now the joining of two relations. RelOptInfo.pathlist are various
|
||||||
paths to create the joined result, having different orderings depending
|
paths to create the joined result, having different orderings depending
|
||||||
on the join method used.
|
on the join method used.
|
||||||
|
|
||||||
@ -30,27 +29,34 @@ a new relation added to each RelOptInfo. This continues until all
|
|||||||
relations have been joined into one RelOptInfo, and the cheapest Path is
|
relations have been joined into one RelOptInfo, and the cheapest Path is
|
||||||
chosen.
|
chosen.
|
||||||
|
|
||||||
SELECT *
|
SELECT *
|
||||||
FROM tab1, tab2, tab3, tab4
|
FROM tab1, tab2, tab3, tab4
|
||||||
WHERE tab1.col = tab2.col AND
|
WHERE tab1.col = tab2.col AND
|
||||||
tab2.col = tab3.col AND
|
tab2.col = tab3.col AND
|
||||||
tab3.col = tab4.col
|
tab3.col = tab4.col
|
||||||
|
|
||||||
Tables 1, 2, 3, and 4 are joined as:
|
Tables 1, 2, 3, and 4 are joined as:
|
||||||
{1 2},{2 3},{3 4}
|
{1 2},{2 3},{3 4}
|
||||||
{1 2 3},{2 3 4}
|
{1 2 3},{2 3 4}
|
||||||
{1 2 3 4}
|
{1 2 3 4}
|
||||||
|
|
||||||
SELECT *
|
SELECT *
|
||||||
FROM tab1, tab2, tab3, tab4
|
FROM tab1, tab2, tab3, tab4
|
||||||
WHERE tab1.col = tab2.col AND
|
WHERE tab1.col = tab2.col AND
|
||||||
tab1.col = tab3.col AND
|
tab1.col = tab3.col AND
|
||||||
tab1.col = tab4.col
|
tab1.col = tab4.col
|
||||||
|
|
||||||
Tables 1, 2, 3, and 4 are joined as:
|
Tables 1, 2, 3, and 4 are joined as:
|
||||||
{1 2},{1 3},{1 4}
|
{1 2},{1 3},{1 4}
|
||||||
{1 2 3},{1 3 4},{1,2,4}
|
{1 2 3},{1 3 4},{1,2,4}
|
||||||
{1 2 3 4}
|
{1 2 3 4}
|
||||||
|
|
||||||
|
In the default left-handed joins, each RelOptInfo adds one
|
||||||
|
single-relation RelOptInfo in each join pass, and the added RelOptInfo
|
||||||
|
is always the inner relation in the join. In right-handed joins, the
|
||||||
|
added RelOptInfo is the outer relation in the join. In bushy plans,
|
||||||
|
multi-relation RelOptInfo's can be joined to other multi-relation
|
||||||
|
RelOptInfo's.
|
||||||
|
|
||||||
Optimizer Functions
|
Optimizer Functions
|
||||||
-------------------
|
-------------------
|
||||||
@ -95,28 +101,28 @@ planner()
|
|||||||
---subplanner()
|
---subplanner()
|
||||||
make list of relations in target
|
make list of relations in target
|
||||||
make list of relations in where clause
|
make list of relations in where clause
|
||||||
split up the qual into restrictions (a=1) and joins (b=c)
|
split up the qual into restrictions (a=1) and joins (b=c)
|
||||||
find which relations can do merge sort and hash joins
|
find relation clauses can do merge sort and hash joins
|
||||||
----find_paths()
|
----make_one_rel()
|
||||||
find scan and all index paths for each relation not yet joined
|
set_base_rel_pathlist()
|
||||||
one relation, return
|
find scan and all index paths for each relation
|
||||||
find selectivity of columns used in joins
|
find selectivity of columns used in joins
|
||||||
-----find_join_paths()
|
-----make_one_rel_by_joins()
|
||||||
jump to geqo if needed
|
jump to geqo if needed
|
||||||
again:
|
again:
|
||||||
find_join_rels():
|
make_rels_by_joins():
|
||||||
for each joinrel:
|
for each joinrel:
|
||||||
find_clause_joins()
|
make_rels_by_clause_joins()
|
||||||
for each join on joinrel:
|
for each rel's joininfo list:
|
||||||
if a join from the join clause adds only one relation, do the join
|
if a join from the join clause adds only one relation, do the join
|
||||||
or find_clauseless_joins()
|
or make_rels_by_clauseless_joins()
|
||||||
find_all_join_paths()
|
update_rels_pathlist_for_joins()
|
||||||
generate paths(nested,sortmerge) for joins found in find_join_rels()
|
generate nested,merge,hash join paths for new rel's created above
|
||||||
prune_joinrels()
|
merge_rels_with_same_relids()
|
||||||
remove from the join list the relation we just added to each join
|
merge RelOptInfo paths that have the same relids because of joins
|
||||||
prune_rel_paths()
|
rels_set_cheapest()
|
||||||
set cheapest and perhaps remove unordered path, recompute table sizes
|
set cheapest path
|
||||||
if we have not done all the tables, go to again:
|
if all relations in one RelOptInfo, return
|
||||||
do group(GROUP)
|
do group(GROUP)
|
||||||
do aggregate
|
do aggregate
|
||||||
put back constants
|
put back constants
|
||||||
@ -129,17 +135,15 @@ planner()
|
|||||||
Optimizer Structures
|
Optimizer Structures
|
||||||
--------------------
|
--------------------
|
||||||
|
|
||||||
RelOptInfo - Every relation
|
RelOptInfo - a relation or joined relations
|
||||||
|
|
||||||
RestrictInfo - restriction clauses
|
RestrictInfo - restriction clauses
|
||||||
JoinInfo - join combinations
|
JoinInfo - join clauses
|
||||||
|
|
||||||
Path - every way to access a relation(sequential, index)
|
Path - every way to generate a RelOptInfo(sequential,index,joins)
|
||||||
IndexPath - index scans
|
IndexPath - index scans
|
||||||
|
NestPath - nested joins
|
||||||
JoinPath - joins
|
MergePath - merge joins
|
||||||
MergePath - merge joins
|
HashPath - hash joins
|
||||||
HashPath - hash joins
|
|
||||||
|
|
||||||
PathOrder - every ordering type (sort, merge of relations)
|
|
||||||
|
|
||||||
|
PathOrder - every ordering type (sort, merge of relations)
|
||||||
|
Loading…
x
Reference in New Issue
Block a user