X-Original-To: pgsql-performance-postgresql.org@postgresql.org Received: from localhost (wm.hub.org [200.46.204.128]) by postgresql.org (Postfix) with ESMTP id C9C7A9FB1BF for ; Sat, 22 Jul 2006 14:04:10 -0300 (ADT) Received: from postgresql.org ([200.46.204.71]) by localhost (mx1.hub.org [200.46.204.128]) (amavisd-new, port 10024) with ESMTP id 85788-03 for ; Sat, 22 Jul 2006 17:04:00 +0000 (UTC) X-Greylist: from auto-whitelisted by SQLgrey- Received: from sss.pgh.pa.us (sss.pgh.pa.us [66.207.139.130]) by postgresql.org (Postfix) with ESMTP id A20669FB1BE for ; Sat, 22 Jul 2006 14:04:01 -0300 (ADT) Received: from sss2.sss.pgh.pa.us (tgl@localhost [127.0.0.1]) by sss.pgh.pa.us (8.13.6/8.13.6) with ESMTP id k6MH3wje027059; Sat, 22 Jul 2006 13:03:58 -0400 (EDT) To: "Guillaume Smet" cc: "Kevin McArthur" , pgsql-performance@postgresql.org Subject: Re: Bad Planner Statistics for Uneven distribution. In-reply-to: <1d4e0c10607211500t62be09f2v8284ceb5176b01bc@mail.gmail.com> References: <003b01c6acf1$a66d8910$0701a8c0@kdesktop> <8073.1153517393@sss.pgh.pa.us> <1d4e0c10607211500t62be09f2v8284ceb5176b01bc@mail.gmail.com> Comments: In-reply-to "Guillaume Smet" message dated "Sat, 22 Jul 2006 00:00:01 +0200" Date: Sat, 22 Jul 2006 13:03:58 -0400 Message-ID: <27058.1153587838@sss.pgh.pa.us> From: Tom Lane X-Virus-Scanned: Maia Mailguard 1.0.1 X-Archive-Number: 200607/220 X-Sequence-Number: 20080 "Guillaume Smet" writes: > Isn't there any way to make PostgreSQL have a better estimation here: > -> Index Scan using models_brands_brand on models_brands > (cost=0.00..216410.97 rows=92372 width=0) (actual time=0.008..0.008 > rows=0 loops=303) > Index Cond: (brand = $0) Note that the above plan extract is pretty misleading, because it doesn't account for the implicit "LIMIT 1" of an EXISTS() clause. What the planner is *actually* imputing to this plan is 216410.97/92372 cost units, or about 2.34. However that applies to the seqscan variant as well. I think the real issue with Kevin's example is that when doing an EXISTS() on a brand_id that doesn't actually exist in the table, the seqscan plan has worst-case behavior (ie, scan the whole table) while the indexscan plan still manages to be cheap. Because his brands table has so many brand_ids that aren't in the table, that case dominates the results. Not sure how we could factor that risk into the cost estimates. The EXISTS code could probably special-case it reasonably well for the simplest seqscan and indexscan subplans, but I don't see what to do with more general subqueries (like joins). regards, tom lane