Received: from malur.postgresql.org ([217.196.149.56]) by arkaria.postgresql.org with esmtp (Exim 4.80) (envelope-from ) id 1XtNCf-0002jU-3j for pgsql-performance@arkaria.postgresql.org; Tue, 25 Nov 2014 20:59:17 +0000 Received: from localhost ([127.0.0.1] helo=postgresql.org) by malur.postgresql.org with smtp (Exim 4.80) (envelope-from ) id 1XtNCe-0006Jd-Bd for pgsql-performance@arkaria.postgresql.org; Tue, 25 Nov 2014 20:59:16 +0000 Received: from magus.postgresql.org ([2a02:c0:301:0:ffff::29]) by malur.postgresql.org with esmtps (TLS1.2:DHE_RSA_AES_256_CBC_SHA256:256) (Exim 4.80) (envelope-from ) id 1XtNCd-0006JW-7u for pgsql-performance@postgresql.org; Tue, 25 Nov 2014 20:59:15 +0000 Received: from smtp-outbound-1.vmware.com ([208.91.2.12]) by magus.postgresql.org with esmtps (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:256) (Exim 4.80) (envelope-from ) id 1XtNCX-0004fV-GS for pgsql-performance@postgresql.org; Tue, 25 Nov 2014 20:59:14 +0000 Received: from sc9-mailhost1.vmware.com (sc9-mailhost1.vmware.com [10.113.161.71]) by smtp-outbound-1.vmware.com (Postfix) with ESMTP id 8682A28B2D; Tue, 25 Nov 2014 12:59:03 -0800 (PST) Received: from EX13-CAS-007.vmware.com (EX13-CAS-007.vmware.com [10.113.191.57]) by sc9-mailhost1.vmware.com (Postfix) with ESMTP id 82A71195DE; Tue, 25 Nov 2014 12:59:03 -0800 (PST) Received: from EX13-MBX-024.vmware.com (10.113.191.44) by EX13-MBX-010.vmware.com (10.113.191.30) with Microsoft SMTP Server (TLS) id 15.0.913.22; Tue, 25 Nov 2014 12:59:23 -0800 Received: from [192.168.1.90] (10.113.160.246) by EX13-MBX-024.vmware.com (10.113.191.44) with Microsoft SMTP Server (TLS) id 15.0.913.22; Tue, 25 Nov 2014 12:58:57 -0800 Message-ID: <5474ED7C.9030403@vmware.com> Date: Tue, 25 Nov 2014 22:58:36 +0200 From: Heikki Linnakangas Organization: VMware User-Agent: Mozilla/5.0 (X11; Linux x86_64; rv:31.0) Gecko/20100101 Icedove/31.2.0 MIME-Version: 1.0 To: Scott Marlowe , pgsql-performance Subject: Re: Small performance regression in 9.2 has a big impact References: In-Reply-To: Content-Type: text/plain; charset="utf-8"; format=flowed Content-Transfer-Encoding: 7bit X-Originating-IP: [10.113.160.246] X-ClientProxiedBy: EX13-CAS-013.vmware.com (10.113.191.65) To EX13-MBX-024.vmware.com (10.113.191.44) X-Pg-Spam-Score: -6.9 (------) 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 11/25/2014 10:36 PM, Scott Marlowe wrote: > OK so there's a simple set of tree functions we use at work. They're > quite fast in 8.4 and they've gotten about 40% slower in 9.2. They're > a simple mix of sql and plpgsql functions which are at > http://pastebin.com/SXTnNhd5 and which I've attached. > > Here's a test query: > > select tree_ancestor_keys('000000000000000100000001'); > > According to explain analyze on both 8.4 and 9.2 they have the same > plan. However, on the same machine the query is about 40% slower on > 9.2. Note we're not hitting the disks, or even buffers here. It's pure > in memory plpsql and sql that we're running. > > explain analyze select tree_ancestor_keys('000000000000000100000001') > from generate_series(1,1000); > > On 8.4 runs in about 280 to 300 ms. (you can run it once and get the > same diff, it's just easier to see with the generate series forcing it > to run 1000 times to kind of even out the noise.) > > On 9.2, same machine, clean fresh dbs etc, it runs in ~400 ms. And > that difference seems to be there on all plpgsql and sql functions. > > In our application, these tree functions get called millions and > millions of times a day, and a 40% performance penalty is a pretty big > deal. > > We're already using the trick of telling the query planner that this > function will return 1 row with alter function rows 1 etc. That helps > a lot but it doesn't fix this underlying performance issue. > > Server versions are 8.4.22 (last I think) and 9.2.9. > > If anyone has any suggestions I'd love to hear them. I don't know why this regressed between those versions, but looking at the functions, there's some low-hanging fruit: 1. tree_ancestor_keys() could use UNION ALL instead of UNION. (I believe duplicates are expected here, although I'm not 100% sure). 2. tree_ancestor_keys() calculates tree_level($1) every time it recurses. Would be cheaper to calculate once, and pass it as argument. Put together: CREATE FUNCTION tree_ancestor_keys(bit varying, integer, integer) RETURNS SETOF bit varying LANGUAGE sql IMMUTABLE STRICT AS $_$ select tree_ancestor_key($1, $2) union all select tree_ancestor_keys($1, $2 + 1, $3) where $2 < $3 $_$; CREATE or replace FUNCTION tree_ancestor_keys(bit varying, integer) RETURNS SETOF bit varying LANGUAGE sql IMMUTABLE STRICT AS $_$ select tree_ancestor_keys($1, $2 + 1, tree_level($1)) $_$; These changes make your test query go about 2x faster on my laptop, with git master. I'm sure you could optimize the functions further, but those at least seem like fairly safe and simple changes. - Heikki -- Sent via pgsql-performance mailing list (pgsql-performance@postgresql.org) To make changes to your subscription: http://www.postgresql.org/mailpref/pgsql-performance