Received: from malur.postgresql.org ([217.196.149.56]) by arkaria.postgresql.org with esmtp (Exim 4.72) (envelope-from ) id 1URKGO-0003V7-MJ for pgsql-performance@arkaria.postgresql.org; Sun, 14 Apr 2013 10:34:24 +0000 Received: from localhost ([127.0.0.1] helo=postgresql.org) by malur.postgresql.org with smtp (Exim 4.72) (envelope-from ) id 1URKGN-0006sd-Ku for pgsql-performance@arkaria.postgresql.org; Sun, 14 Apr 2013 10:34:23 +0000 Received: from magus.postgresql.org ([2a02:c0:301:0:ffff::29]) by malur.postgresql.org with esmtp (Exim 4.72) (envelope-from ) id 1URKGM-0006sY-QX for pgsql-performance@postgresql.org; Sun, 14 Apr 2013 10:34:22 +0000 Received: from mail-ee0-f43.google.com ([74.125.83.43]) by magus.postgresql.org with esmtp (Exim 4.72) (envelope-from ) id 1URKGJ-0003Mc-8W for pgsql-performance@postgresql.org; Sun, 14 Apr 2013 10:34:21 +0000 Received: by mail-ee0-f43.google.com with SMTP id e50so1859678eek.2 for ; Sun, 14 Apr 2013 03:34:17 -0700 (PDT) X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=20120113; h=x-received:date:from:to:cc:subject:message-id:in-reply-to :references:organization:x-mailer:mime-version:content-type :content-transfer-encoding:x-gm-message-state; bh=/geVcV/0H7dCZuYMBlro1Vj2673D5Tq1/VNASE3xaTY=; b=hq28OOH9+G39VggEKx/WRyqssJ19dn2KueI3bdmciEaoDmclf2xqnD5g8z1KHPzaf9 frf6jdJn23RXIBCgRnbDines9DzlPf9nWcxauFc1oe/iC3ZhA5thr4skILGxA/sKtmC9 oFaBDujq2NgWDt5Unxf+MeYlSWCx9vq2aIPnc5bUOAsw/cCkfxiYfJK6k7qGegPnIIEk fbfAG/P5moGcfOgk2bf1zHK2zu1QNzP7vw82qRrDIqEXilVTHi88nl4vARswpKbM+AXh 7Yd7tsYG+w2L5TEXSM8sLsS51P2Mg9kokSAJvUticpSRS8h32KNROr5fjYaUsm2CynVv kf/Q== X-Received: by 10.14.218.66 with SMTP id j42mr48831387eep.46.1365935657500; Sun, 14 Apr 2013 03:34:17 -0700 (PDT) Received: from unknown (cpezg-94-253-149-80-cbl.xnet.hr. [94.253.149.80]) by mx.google.com with ESMTPS id d47sm20842632eem.9.2013.04.14.03.34.15 (version=TLSv1 cipher=RC4-SHA bits=128/128); Sun, 14 Apr 2013 03:34:16 -0700 (PDT) Date: Sun, 14 Apr 2013 12:34:14 +0200 From: Rikard Pavelic To: Tom Lane Cc: pgsql-performance@postgresql.org Subject: Re: limit is sometimes not pushed in view with order Message-ID: <20130414123414.00000718@unknown> In-Reply-To: <20130413200816.00007f1b@unknown> References: <5169168D.4000903@ngs.hr> <2583.1365866479@sss.pgh.pa.us> <20130413200816.00007f1b@unknown> Organization: N.G.S. X-Mailer: Claws Mail 3.7.8cvs47 (GTK+ 2.16.6; i586-pc-mingw32msvc) Mime-Version: 1.0 Content-Type: text/plain; charset=US-ASCII Content-Transfer-Encoding: 7bit X-Gm-Message-State: ALoCoQkoBF/Ltqsjxpm/UP+CTVeS83xu+SbmsGc1kEvjBaWsps4saDrztkIlZMAK69O+/xaZIDAy X-Pg-Spam-Score: -2.6 (--) List-Archive: List-Help: List-ID: List-Owner: List-Post: List-Subscribe: List-Unsubscribe: X-Mailing-List: pgsql-performance Precedence: bulk Sender: pgsql-performance-owner@postgresql.org On Sat, 13 Apr 2013 20:08:16 +0200 Rikard Pavelic wrote: > While one could argue that optimizer doesn't know to optimize left > join with group by its primary key, you can replace that join with > some other joins (ie left join to another table pk) and the same > behavior will be displayed (joining all tables and applying limit at > the end). > That's why I asked if fence for pushing limit is a known behavior. While I can work around that problem by pushing left join in select subquery this doesn't solve all problems since limit is not pushed down on nontrivial queries. This is probably the best example: create table big_table(i serial primary key, delay int); create function some_calculation(i int) returns int as $$ begin perform pg_sleep(i); return i*i; end $$ language plpgsql stable cost 100000; create view big_view as select t.i, some_calculation(t.delay) as calc, s.delay as d2 from big_table t left join big_table s on t.i = s.i + s.i order by t.i asc; insert into big_table select i, i%5 from generate_series(1, 100000) i; analyze big_table; explain analyze select * from big_view v where i >= 100 and i <= 105 limit 1; Limit (cost=3201.63..3201.64 rows=1 width=12) (actual time=10017.471..10017.471 rows=1 loops=1) -> Sort (cost=3201.63..3201.64 rows=5 width=12) (actual time=10017.469..10017.469 rows=1 loops=1) Sort Key: t.i Sort Method: top-N heapsort Memory: 25kB -> Hash Right Join (cost=8.52..3201.57 rows=5 width=12) (actual time=0.078..10017.436 rows=6 loops=1) Hash Cond: ((s.i + s.i) = t.i) -> Seq Scan on big_table s (cost=0.00..1443.00 rows=100000 width=8) (actual time=0.005..6.294 rows=100000 loops=1) -> Hash (cost=8.46..8.46 rows=5 width=8) (actual time=0.012..0.012 rows=6 loops=1) Buckets: 1024 Batches: 1 Memory Usage: 1kB -> Index Scan using big_table_pkey on big_table t (cost=0.00..8.46 rows=5 width=8) (actual time=0.007..0.008 rows=6 loops=1) Index Cond: ((i >= 100) AND (i <= 105)) Total runtime: 10017.514 ms explain analyze select * from big_view v where i >= 100 and i <= 10005 limit 1; Limit (cost=0.00..2391.22 rows=1 width=12) (actual time=0.088..0.088 rows=1 loops=1) -> Nested Loop Left Join (cost=0.00..23780547.26 rows=9945 width=12) (actual time=0.087..0.087 rows=1 loops=1) Join Filter: (t.i = (s.i + s.i)) Rows Removed by Join Filter: 49 -> Index Scan using big_table_pkey on big_table t (cost=0.00..359.26 rows=9945 width=8) (actual time=0.014..0.014 rows=1 loops=1) Index Cond: ((i >= 100) AND (i <= 10005)) -> Materialize (cost=0.00..2334.00 rows=100000 width=8) (actual time=0.009..0.020 rows=50 loops=1) -> Seq Scan on big_table s (cost=0.00..1443.00 rows=100000 width=8) (actual time=0.005..0.010 rows=50 loops=1) Total runtime: 0.122 ms explain analyze select * from big_view v where i >= 100 and i <= 10005 limit 10; takes too long... To me this looks like it should be fixable if limit is applied before all targets are evaluated. If I remove the left join from the view, Postgres works as expected, so I guess it already knows how to apply limit before selects, but this is probably missing for subqueries where targets are pulled out of it. Maybe this is a problem since you would probably need closures to pull of a general solution, but there are plenty of use cases without group by that would benefit from applying limit before evaluating targets that are used only in topmost result. So, I was wondering if this is a known problem and is there any interest in tackling it? Regards, Rikard -- Sent via pgsql-performance mailing list (pgsql-performance@postgresql.org) To make changes to your subscription: http://www.postgresql.org/mailpref/pgsql-performance