Received: from maia.hub.org (maia-2.hub.org [200.46.204.251]) by mail.postgresql.org (Postfix) with ESMTP id CC922133798E for ; Thu, 11 Nov 2010 18:37:57 -0400 (AST) Received: from mail.postgresql.org ([200.46.204.86]) by maia.hub.org (mx1.hub.org [200.46.204.251]) (amavisd-maia, port 10024) with ESMTP id 63730-10 for ; Thu, 11 Nov 2010 22:37:51 +0000 (UTC) X-Greylist: from auto-whitelisted by SQLgrey-1.7.6 Received: from sss.pgh.pa.us (sss.pgh.pa.us [66.207.139.130]) by mail.postgresql.org (Postfix) with ESMTP id 892041336971 for ; Thu, 11 Nov 2010 18:37:50 -0400 (AST) Received: from sss2.sss.pgh.pa.us (tgl@localhost [127.0.0.1]) by sss.pgh.pa.us (8.14.2/8.14.2) with ESMTP id oABMbnbd023148; Thu, 11 Nov 2010 17:37:49 -0500 (EST) To: Ben cc: pgsql-performance@postgresql.org Subject: Re: equivalent queries lead to different query plans for self-joins with group by? In-reply-to: <5D061DAC-31E2-4C47-AE3B-7799118C57D3@gmail.com> References: <5D061DAC-31E2-4C47-AE3B-7799118C57D3@gmail.com> Comments: In-reply-to Ben message dated "Thu, 11 Nov 2010 13:52:57 -0800" Date: Thu, 11 Nov 2010 17:37:49 -0500 Message-ID: <23147.1289515069@sss.pgh.pa.us> From: Tom Lane X-Virus-Scanned: Maia Mailguard 1.0.1 X-Spam-Status: No, hits=-1.91 tagged_above=-10 required=5 tests=BAYES_00=-1.9, T_RP_MATCHES_RCVD=-0.01 X-Spam-Level: X-Archive-Number: 201011/176 X-Sequence-Number: 41200 Ben writes: > us_quotedb=# explain select ts, id, val - aval from foo join (select ts, avg(val) as aval from foo group by ts) as a using (ts) where ts > '2010-11-11' and ts < '2010-11-13'; > on the other hand, if i specify "which" timestamp i'm restricting, it appears to do the right thing: > us_quotedb=# explain select ts, id, val - aval from foo join (select ts, avg(val) as aval from foo group by ts) as a using (ts) where a.ts > '2010-11-11' and a.ts < '2010-11-13'; Well, arguably it's not doing the right thing either way --- you'd sort of like the inequalities to get pushed down into both of the join inputs, not just one of them. PG doesn't make that deduction though; it can make such inferences for equalities, but inequalities are not optimized as much. The case where you have "using (ts) where ts > ..." is, I believe, interpreted as though you'd specified the left-hand join input, ie "using (ts) where foo.ts > ...". So the range condition is pushed into the foo scan, which doesn't help the avg() subquery. When you specify the restriction against "a", it's pushed into the subquery where it's more useful. You could try "where foo.ts > ... and a.ts > ..." but not sure if it's really worth the trouble here, at least not if those rowcount estimates are anywhere near accurate. If you were doing the join across quite a lot of rows, having the constraints in both subqueries would be useful. regards, tom lane