favBeersselect intoselect into❖ Week 04 Monday |
cs3311@cse❖ Week 04 Monday (cont) |
❖ PostgreSQL Stored Procedures |
PostgreSQL syntax for defining stored functions:
create or replace function funcName(arg1, arg2, ....) returns retType as $$ String containing function definition $$ language funcDefLanguage;
Notes:
$$$$''❖ Withdrawal Function in PLpgSQL |
create or replace function
withdraw(_acctNum text, _amount integer) returns text
as $$
declare bal integer;
begin
select balance into bal
from Accounts
where acctNo = _acctNum);
if (bal < _amount) then
return 'Insufficient Funds';
else
update Accounts
set balance = balance - _amount
where acctNo = _acctNum;
bal := bal - _amount;
return 'New Balance: ' || bal;
end if
end;
❖ SQL functions |
The body of a PostgreSQL function can be an SQL query
create or replace function maxPriceAt(text) returns numeric(4,2) as $$ select max(price)::numeric(4,2) from Sells where bar = $1; $$ language sql;
which can be used as, e.g.
select * from maxPriceAt('Royal Hotel');
select maxPriceAt('Coogee Bay Hotel');
select name, maxPriceAt(name) from Bars;
But still provides no procedural programming capability
❖ SQL functions (cont) |
Value returned by an SQL function ...
selectcreate or replace function maxPriceAt(_bar text) returns numeric(4,2) as $$ select max(price)::numeric(4,2) from Sells where bar = _bar; $$ language sql;
❖ Exercise: SQL function |
Write an SQL function to find the most expensive beer that a drinker likes
create or replace function priciest(_drinker text) returns text as $$ ... $$ language sql;
❖ PLpgSQL |
PLpgSQL is PostgreSQL's stored procedure language
Allows you to write functions that combine
Loosely based on Oracle's PL/SQL (translating between PL/SQL and PLpgSQL is easy)
❖ Example PLpgSQL function (i) |
An iterative factorial function in PLpgSQL
create or replace function ifac(n integer) returns integer as $$ declare i integer; --uninitialised variable fac integer := 1; -- initialised variable begin for i in 2..n loop fac := fac * i; end loop; return fac; end; $$ language plpgsql;
❖ Example PLpgSQL function (ii) |
A recursive factorial function in PLpgSQL
create or replace function
rfac(n integer) returns integer
as $$
begin
if (n < 2) then
return 1;
else
return n * rfac(n-1);
end if;
end;
$$ language plpgsql;
❖ PLpgSQL functions returning Sets |
PLpgSQL functions can return sets of values, e.g.
create or replace function iota(_max integer) return setof integer as $$ ... $$
If they return a set of tuples, they effectively return a table, e.g.
create or replace function favBeers(_drinker text) return setof Beers as $$ ... $$
Each tuple/value is included in the result set by return nextValue
❖ Exercise: Function Overloading |
A function is identified by its name and parameter types (its signature).
Can have several functions with same name, but different parameters.
Consider a function seq
seq(n)seq(n,m)seq(n,m,incr)seq()❖ PLpgSQL function returning Sets of Tuples |
As noted above, functions can return sets of tuples.
Return sets can be defined:
function F(...) returns table(x integer, y integer)
create type Pair as (x integer, y integer); function F(...) returns setof Pair
create table Beers (id integer, name text, ...); function F(...) returns setof Beers
❖ PLpgSQL function returning Sets of Tuples (cont) |
Individual tuples are added to result set via RETURN NEXT
How this is acheived differs between the methods.
F(...) returns table(x integer, y integer)xyRETURN NEXT;F(...) returns set of PairpPairp.xp.yRETURN NEXT p;❖ PLpgSQL functions using queries |
PLpgSQL functions can invoke queries and iterate through their results
Example:
create function
beersLike(partName text) returns setof Beers
as $$
declare
tuple Beers;
begin
for tuple in
select * from Beers where name ~* partName
loop
return next tuple;
end loop;
end;
$$ language plpgsql;
❖ PLpgSQL functions using queries (cont) |
Deferred typing of query variables:
declare
tuple record;
begin
for tuple in Query
loop
Process tuple
end loop;
...
end;
The tuple
I.e. the type of a record
❖ Exercise: The favBeers |
Implement a the favourite beers function
create or replace function favBeers(_drinker text) returns setof Beers as $$ ... $$ language plpgsql;
Assume that every beer a drinker drinks is one of their favourites
❖ Functions vs Views |
Functions returning setof
Views are used like tables.
What's the difference?
❖ Exercise: Function vs View |
Consider a view that gives Drinkers, but without their phone:
create or replace view d1(drinker,surburb) as ...
Then implement the same thing as a function
Then add parameter to restrict to names matching pattern
❖ select into |
Can capture individual attributes in a select statement
select att1, att2, ... attn into var1, var2, ... varn from ...
Notes:
attiattivaricreate table R (...); declare tup R; select * into tup from R where Condition;
❖ Exercise: select into |
Consider a table R(a integer, b text, c float)
Implement different ways to collect individual attributes into variables
Variables are x integer, y text, z float
Produced: 2 Oct 2023