Movatterモバイル変換


[0]ホーム

URL:


Skip to content

Navigation Menu

Sign in
Appearance settings

Search code, repositories, users, issues, pull requests...

Provide feedback

We read every piece of feedback, and take your input very seriously.

Saved searches

Use saved searches to filter your results more quickly

Sign up
Appearance settings

Commitc40ba5f

Browse files
committed
Fix rowcount estimate for SubqueryScan that's under a Gather.
SubqueryScan was always getting labeled with a rowcount estimateappropriate for non-parallel cases. However, nodes that areunderneath a Gather should be treated as processing only oneworker's share of the rows, whether the particular node is explicitlyparallel-aware or not. Most non-scan-level node types get thisright automatically because they base their rowcount estimate onthat of their input sub-Path(s). But SubqueryScan didn't do that,instead using the whole-relation rowcount estimate as if it werea non-parallel-aware scan node. If there is a parallel-aware nodebelow the SubqueryScan, this is wrong, and it results in inflatingthe cost estimates for nodes above the SubqueryScan, which can causeus to not choose a parallel plan, or choose a silly one --- as indeedis visible in the one regression test whose results change with thispatch. (Although that plan tree appears to contain no SubqueryScans,there were some in it before setrefs.c deleted them.)To fix, use path->subpath->rows not baserel->tuples as the numberof input tuples we'll process. This requires estimating the quals'selectivity afresh, which is slightly annoying; but it shouldn'treally add much cost thanks to the caching done in RestrictInfo.This is pretty clearly a bug fix, but I'll refrain from back-patchingas people might not appreciate plan choices changing in stable branches.The fact that it took us this long to identify the bug suggests thatit's not a major problem.Per report from bucoo, though this is not his proposed patch.Discussion:https://postgr.es/m/202204121457159307248@sohu.com
1 parentdc2be6e commitc40ba5f

File tree

2 files changed

+22
-10
lines changed

2 files changed

+22
-10
lines changed

‎src/backend/optimizer/path/costsize.c

Lines changed: 18 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1395,18 +1395,32 @@ cost_subqueryscan(SubqueryScanPath *path, PlannerInfo *root,
13951395
{
13961396
Coststartup_cost;
13971397
Costrun_cost;
1398+
List*qpquals;
13981399
QualCostqpqual_cost;
13991400
Costcpu_per_tuple;
14001401

14011402
/* Should only be applied to base relations that are subqueries */
14021403
Assert(baserel->relid>0);
14031404
Assert(baserel->rtekind==RTE_SUBQUERY);
14041405

1405-
/* Mark the path with the correct row estimate */
1406+
/*
1407+
* We compute the rowcount estimate as the subplan's estimate times the
1408+
* selectivity of relevant restriction clauses. In simple cases this will
1409+
* come out the same as baserel->rows; but when dealing with parallelized
1410+
* paths we must do it like this to get the right answer.
1411+
*/
14061412
if (param_info)
1407-
path->path.rows=param_info->ppi_rows;
1413+
qpquals=list_concat_copy(param_info->ppi_clauses,
1414+
baserel->baserestrictinfo);
14081415
else
1409-
path->path.rows=baserel->rows;
1416+
qpquals=baserel->baserestrictinfo;
1417+
1418+
path->path.rows=clamp_row_est(path->subpath->rows*
1419+
clauselist_selectivity(root,
1420+
qpquals,
1421+
0,
1422+
JOIN_INNER,
1423+
NULL));
14101424

14111425
/*
14121426
* Cost of path is cost of evaluating the subplan, plus cost of evaluating
@@ -1421,7 +1435,7 @@ cost_subqueryscan(SubqueryScanPath *path, PlannerInfo *root,
14211435

14221436
startup_cost=qpqual_cost.startup;
14231437
cpu_per_tuple=cpu_tuple_cost+qpqual_cost.per_tuple;
1424-
run_cost=cpu_per_tuple*baserel->tuples;
1438+
run_cost=cpu_per_tuple*path->subpath->rows;
14251439

14261440
/* tlist eval costs are paid per output row, not per tuple scanned */
14271441
startup_cost+=path->path.pathtarget->cost.startup;

‎src/test/regress/expected/incremental_sort.out

Lines changed: 4 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -1487,14 +1487,12 @@ explain (costs off) select * from t union select * from t order by 1,3;
14871487
-> Unique
14881488
-> Sort
14891489
Sort Key: t.a, t.b, t.c
1490-
->Append
1491-
-> Gather
1492-
Workers Planned: 2
1490+
->Gather
1491+
Workers Planned: 2
1492+
-> Parallel Append
14931493
-> Parallel Seq Scan on t
1494-
-> Gather
1495-
Workers Planned: 2
14961494
-> Parallel Seq Scan on t t_1
1497-
(13 rows)
1495+
(11 rows)
14981496

14991497
-- Full sort, not just incremental sort can be pushed below a gather merge path
15001498
-- by generate_useful_gather_paths.

0 commit comments

Comments
 (0)

[8]ページ先頭

©2009-2025 Movatter.jp