From b1577a7c78d2d8880b3c0f94689fb75bd074c897 Mon Sep 17 00:00:00 2001 From: Tom Lane Date: Tue, 15 Feb 2000 20:49:31 +0000 Subject: New cost model for planning, incorporating a penalty for random page accesses versus sequential accesses, a (very crude) estimate of the effects of caching on random page accesses, and cost to evaluate WHERE- clause expressions. Export critical parameters for this model as SET variables. Also, create SET variables for the planner's enable flags (enable_seqscan, enable_indexscan, etc) so that these can be controlled more conveniently than via PGOPTIONS. Planner now estimates both startup cost (cost before retrieving first tuple) and total cost of each path, so it can optimize queries with LIMIT on a reasonable basis by interpolating between these costs. Same facility is a win for EXISTS(...) subqueries and some other cases. Redesign pathkey representation to achieve a major speedup in planning (I saw as much as 5X on a 10-way join); also minor changes in planner to reduce memory consumption by recycling discarded Path nodes and not constructing unnecessary lists. Minor cleanups to display more-plausible costs in some cases in EXPLAIN output. Initdb forced by change in interface to index cost estimation functions. --- src/backend/commands/explain.c | 40 +++++++++++++--------------------------- 1 file changed, 13 insertions(+), 27 deletions(-) (limited to 'src/backend/commands/explain.c') diff --git a/src/backend/commands/explain.c b/src/backend/commands/explain.c index 2b152b2fe5b..2a38a349d60 100644 --- a/src/backend/commands/explain.c +++ b/src/backend/commands/explain.c @@ -5,7 +5,7 @@ * Portions Copyright (c) 1996-2000, PostgreSQL, Inc * Portions Copyright (c) 1994-5, Regents of the University of California * - * $Id: explain.c,v 1.53 2000/02/15 03:36:39 thomas Exp $ + * $Header: /cvsroot/pgsql/src/backend/commands/explain.c,v 1.54 2000/02/15 20:49:08 tgl Exp $ * */ @@ -217,39 +217,24 @@ explain_outNode(StringInfo str, Plan *plan, int indent, ExplainState *es) { relation = RelationIdGetRelation(lfirsti(l)); Assert(relation); - if (++i > 1) - appendStringInfo(str, ", "); - appendStringInfo(str, + appendStringInfo(str, "%s%s", + (++i > 1) ? ", " : "", stringStringInfo(RelationGetRelationName(relation))); /* drop relcache refcount from RelationIdGetRelation */ RelationDecrementReferenceCount(relation); } + /* FALL THRU */ case T_SeqScan: + case T_TidScan: if (((Scan *) plan)->scanrelid > 0) { RangeTblEntry *rte = nth(((Scan *) plan)->scanrelid - 1, es->rtable); - appendStringInfo(str, " on "); - if (strcmp(rte->ref->relname, rte->relname) != 0) - { - appendStringInfo(str, "%s ", - stringStringInfo(rte->relname)); - } - appendStringInfo(str, stringStringInfo(rte->ref->relname)); - } - break; - case T_TidScan: - if (((TidScan *) plan)->scan.scanrelid > 0) - { - RangeTblEntry *rte = nth(((TidScan *) plan)->scan.scanrelid - 1, es->rtable); - - appendStringInfo(str, " on "); - if (strcmp(rte->ref->relname, rte->relname) != 0) - { - appendStringInfo(str, "%s ", - stringStringInfo(rte->relname)); - } - appendStringInfo(str, stringStringInfo(rte->ref->relname)); + appendStringInfo(str, " on %s", + stringStringInfo(rte->relname)); + if (rte->ref && strcmp(rte->ref->relname, rte->relname) != 0) + appendStringInfo(str, " %s", + stringStringInfo(rte->ref->relname)); } break; default: @@ -257,8 +242,9 @@ explain_outNode(StringInfo str, Plan *plan, int indent, ExplainState *es) } if (es->printCost) { - appendStringInfo(str, " (cost=%.2f rows=%.0f width=%d)", - plan->cost, plan->plan_rows, plan->plan_width); + appendStringInfo(str, " (cost=%.2f..%.2f rows=%.0f width=%d)", + plan->startup_cost, plan->total_cost, + plan->plan_rows, plan->plan_width); } appendStringInfo(str, "\n"); -- cgit v1.2.3