means that if a <application>PL/pgSQL</application> function produces a
very large result set, performance might be poor: data will be
written to disk to avoid memory exhaustion, but the function
itself will not return until the entire result set has been
generated. A future version of <application>PL/pgSQL</application> might
allow users to define set-returning functions
that do not have this limitation. Currently, the point at
which data begins being written to disk is controlled by the
<xref linkend="guc-work-mem"/>
configuration variable. Administrators who have sufficient
memory to store larger result sets in memory should consider
increasing this parameter.
</para>
</note>
</sect3>
</sect2>
<sect2 id="plpgsql-statements-returning-procedure">
<title>Returning from a Procedure</title>
<para>
A procedure does not have a return value. A procedure can therefore end
without a <command>RETURN</command> statement. If you wish to use
a <command>RETURN</command> statement to exit the code early, write
just <command>RETURN</command> with no expression.
</para>
<para>
If the procedure has output parameters, the final values of the output
parameter variables will be returned to the caller.
</para>
</sect2>
<sect2 id="plpgsql-statements-calling-procedure">
<title>Calling a Procedure</title>
<para>
A <application>PL/pgSQL</application> function, procedure,
or <command>DO</command> block can call a procedure
using <command>CALL</command>. Output parameters are handled
differently from the way that <command>CALL</command> works in plain
SQL. Each <literal>OUT</literal> or <literal>INOUT</literal>
parameter of the procedure must
correspond to a variable in the <command>CALL</command> statement, and
whatever the procedure returns is assigned back to that variable after
it returns. For example:
<programlisting>
CREATE PROCEDURE triple(INOUT x int)
LANGUAGE plpgsql
AS $$
BEGIN
x := x * 3;
END;
$$;
DO $$
DECLARE myvar int := 5;
BEGIN
CALL triple(myvar);
RAISE NOTICE 'myvar = %', myvar; -- prints 15
END;
$$;
</programlisting>
The variable corresponding to an output parameter can be a simple
variable or a field of a composite-type variable. Currently,
it cannot be an element of an array.
</para>
</sect2>
<sect2 id="plpgsql-conditionals">
<title>Conditionals</title>
<para>
<command>IF</command> and <command>CASE</command> statements let you execute
alternative commands based on certain conditions.
<application>PL/pgSQL</application> has three forms of <command>IF</command>:
<itemizedlist>
<listitem>
<para><literal>IF ... THEN ... END IF</literal></para>
</listitem>
<listitem>
<para><literal>IF ... THEN ... ELSE ... END IF</literal></para>
</listitem>
<listitem>
<para><literal>IF ... THEN ... ELSIF ... THEN ... ELSE ... END IF</literal></para>
</listitem>
</itemizedlist>
and two forms of <command>CASE</command>:
<itemizedlist>
<listitem>
<para><literal>CASE ... WHEN ... THEN ... ELSE ... END CASE</literal></para>
</listitem>
<listitem>
<para><literal>CASE WHEN ... THEN ... ELSE ... END CASE</literal></para>
</listitem>
</itemizedlist>
</para>
<sect3 id="plpgsql-conditionals-if-then">
<title><literal>IF-THEN</literal></title>
<synopsis>
IF <replaceable>boolean-expression</replaceable> THEN
<replaceable>statements</replaceable>
END IF;
</synopsis>
<para>
<literal>IF-THEN</literal> statements are the simplest form of
<literal>IF</literal>. The statements between
<literal>THEN</literal> and <literal>END IF</literal> will be
executed if the condition is true. Otherwise, they are
skipped.
</para>