Received: from maia.hub.org (maia-2.hub.org [200.46.204.251]) by mail.postgresql.org (Postfix) with ESMTP id 3A5F1632AA6 for ; Mon, 21 Jun 2010 04:29:50 -0300 (ADT) 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 52650-08 for ; Mon, 21 Jun 2010 07:29:42 +0000 (UTC) Received: from news.hub.org (news.hub.org [200.46.204.72]) by mail.postgresql.org (Postfix) with ESMTP id 36B106329BE for ; Mon, 21 Jun 2010 04:29:43 -0300 (ADT) Received: from news.hub.org (news.hub.org [200.46.204.72]) by news.hub.org (8.14.4/8.14.4) with ESMTP id o5L7Te5K015319 for ; Mon, 21 Jun 2010 04:29:40 -0300 (ADT) (envelope-from news@news.hub.org) Received: (from news@localhost) by news.hub.org (8.14.4/8.14.4/Submit) id o5L6wScv071558 for pgsql-performance@postgresql.org; Mon, 21 Jun 2010 03:58:28 -0300 (ADT) (envelope-from news) From: "Davor J." X-Newsgroups: pgsql.performance Subject: Re: Slow function in queries SELECT clause. Date: Mon, 21 Jun 2010 08:57:41 +0200 Organization: Hub.Org Networking Services Lines: 56 Message-ID: References: <25116.1277047267@sss.pgh.pa.us> X-Complaints-To: usenet@news.hub.org X-Priority: 3 X-MSMail-Priority: Normal X-Newsreader: Microsoft Outlook Express 6.00.2900.5931 X-RFC2646: Format=Flowed; Original X-MimeOLE: Produced By Microsoft MimeOLE V6.00.2900.5931 To: pgsql-performance@postgresql.org X-Virus-Scanned: Maia Mailguard 1.0.1 X-Spam-Status: No, hits=0.79 tagged_above=-10 required=5 tests=BAYES_50=0.8, T_RP_MATCHES_RCVD=-0.01 X-Spam-Level: X-Archive-Number: 201006/365 X-Sequence-Number: 39221 Thanks Tom, Your concepts of "inlining" and "black box" really cleared things up for me. With fnc_unit_convert() written in SQL and declared as STABLE I indeed have fast performance now. I appreciate the note on the IMMUTABLE part. The table contents should not change in a way to affect the functions. So, as far as I understand the Postgres workings, this shouldn't pose a problem. Regards, Davor "Tom Lane" wrote in message news:25116.1277047267@sss.pgh.pa.us... > "Davor J." writes: >> Suppose 2 functions: factor(int,int) and offset(int, int). >> Suppose a third function: convert(float,int,int) which simply returns >> $1*factor($2,$3)+offset($2,$3) >> All three functions are IMMUTABLE. > > You should write the third function as a SQL function, which'd allow it > to be inlined. > >> VERY FAST (half a second): >> ---------------- >> SELECT data*factor(1,2)+offset(1,2) FROM tbl_data; > > In this case both factor() calls are folded to constants, hence executed > only once. > >> VERY SLOW (a minute): >> ---------------- >> SELECT convert(data, 1, 2) FROM tbl_data; > > Without inlining, there's no hope of any constant-folding here. > The optimizer just sees the plpgsql function as a black box and > can't do anything with it. > > BTW, your later mail shows that the factor() functions are not really > IMMUTABLE, since they select from tables that presumably are subject to > change. The "correct" declaration would be STABLE. If you're relying > on constant-folding to get reasonable application performance, you're > going to have to continue to mislabel them as IMMUTABLE; but be aware > that you're likely to have issues any time you do change the table > contents. The changes won't get reflected into existing query plans. > > regards, tom lane > > -- > Sent via pgsql-performance mailing list (pgsql-performance@postgresql.org) > To make changes to your subscription: > http://www.postgresql.org/mailpref/pgsql-performance >