@@ -7515,6 +7515,8 @@ genericcostestimate(PlannerInfo *root,
75157515 GenericCosts * costs )
75167516{
75177517 IndexOptInfo * index = path -> indexinfo ;
7518+ RelOptInfo * baserel = index -> rel ;
7519+ bool indexonly = (path -> path .pathtype == T_IndexOnlyScan );
75187520 List * indexQuals = get_quals_from_indexclauses (path -> indexclauses );
75197521 List * indexOrderBys = path -> indexorderbys ;
75207522 Cost indexStartupCost ;
@@ -7523,7 +7525,9 @@ genericcostestimate(PlannerInfo *root,
75237525 double indexCorrelation ;
75247526 double numIndexPages ;
75257527 double numIndexTuples ;
7528+ double spc_seq_page_cost ;
75267529 double spc_random_page_cost ;
7530+ double index_random_page_cost ;
75277531 double num_sa_scans ;
75287532 double num_outer_scans ;
75297533 double num_scans ;
@@ -7621,7 +7625,23 @@ genericcostestimate(PlannerInfo *root,
76217625 /* fetch estimated page cost for tablespace containing index */
76227626 get_tablespace_page_costs (index -> reltablespace ,
76237627 & spc_random_page_cost ,
7624- NULL );
7628+ & spc_seq_page_cost );
7629+
7630+ /* If it is an index only scan, random page cost should be incurred for
7631+ * the percentage of pages that need to be fetched from disk for the
7632+ * relation. Considering that, random page cost should be adjusted such
7633+ * that when no tuples are to be fetched from the table, we end up with a
7634+ * sequential page cost, otherwise, we hover betwen that and random
7635+ * page cost for the tablespace.
7636+ *
7637+ * Otherwise, we default to the random page cost for table space.
7638+ */
7639+ if (indexonly )
7640+ index_random_page_cost = Min (spc_seq_page_cost +
7641+ spc_random_page_cost * (1.0 - baserel -> allvisfrac ),
7642+ spc_random_page_cost );
7643+ else
7644+ index_random_page_cost = spc_random_page_cost ;
76257645
76267646 /*
76277647 * Now compute the disk access costs.
@@ -7661,16 +7681,16 @@ genericcostestimate(PlannerInfo *root,
76617681 * share for each outer scan. (Don't pro-rate for ScalarArrayOpExpr,
76627682 * since that's internal to the indexscan.)
76637683 */
7664- indexTotalCost = (pages_fetched * spc_random_page_cost )
7684+ indexTotalCost = (pages_fetched * index_random_page_cost )
76657685 / num_outer_scans ;
76667686 }
76677687 else
76687688 {
76697689 /*
7670- * For a single index scan, we just charge spc_random_page_cost per
7690+ * For a single index scan, we just charge random page cost per
76717691 * page touched.
76727692 */
7673- indexTotalCost = numIndexPages * spc_random_page_cost ;
7693+ indexTotalCost = numIndexPages * index_random_page_cost ;
76747694 }
76757695
76767696 /*
0 commit comments