[英]Return type for function with array_agg()
我正在嘗試創建一個返回字符串數組的 function,我可以在沒有 function 的情況下執行此操作並返回record[]
類型,當我嘗試在 function 中返回該類型的結果時,它說不是支持的。
CREATE OR REPLACE FUNCTION alarmEventList(sampleid integer
, starttime timestamp without time zone
, stoptime timestamp without time zone)
RETURNS text[] AS
$$
DECLARE
result record[];
BEGIN
select array_agg(result)
from (select to_char("Timestamp", 'YYYY-MM-DD HH24:MI:SS'), "AlertLevel"
, "Timestamp" - lag("Timestamp") over (order by "Timestamp")
from "Judgements"
WHERE "SampleID"=sampleid and "Timestamp" >= starttime
and "Timestamp" <= stoptime) as result where "AlertLevel" >0;
return result;
END
$$
表格Judgements
的定義:
ID | SampleID | AlertLevel | Timestamp
integer | integer | integer | timestamp with time zone
1 | 11 | 1 | 2013-09-17 10:36:40
2 | 11 | 0 | 2013-09-17 10:36:45
3 | 11 | 2 | 2013-09-17 10:36:51
我想返回一個text[]
但我找不到使此查詢成為文本類型或字符串的方法。
我想返回這樣的東西:
{"2013-11-21 10:36:40, 1, 10", "etc...etc..."}
一個函數需要聲明一個返回類型。 數組只能基於眾所周知的元素類型。 不允許匿名記錄。 所以創建一個適合您需要的復合類型(除非有一個表或視圖已經定義了行類型)。
CREATE TYPE my_type (
ts text
, alertlevel int
, time_passed interval
);
出於測試目的,您還可以創建一個臨時表來在會話期間注冊復合類型:
CREATE TEMP TABLE my_type ( ...)
(在會話結束時刪除一個臨時表,此后建立在該類型上的任何函數都將被破壞。)
將其用作數組的基本類型。 您可以使用一個簡單的 SQL 函數來實現:
CREATE OR REPLACE FUNCTION foo()
RETURNS my_type[] AS
$func$
SELECT array_agg(result::my_type) -- you must cast the row type!
FROM (
SELECT to_char("Timestamp", 'YYYY-MM-DD HH24:MI:SS')
, "AlertLevel"
, "Timestamp" - lag("Timestamp") OVER (ORDER BY "Timestamp")
FROM "Judgements"
WHERE "SampleID" = sampleid
AND "Timestamp" >= starttime
AND "Timestamp" <= stoptime
) result
WHERE "AlertLevel" > 0;
$func$
LANGUAGE sql;
致電:
SELECT foo();
text[]
簡單替代您還可以轉換為text
/ text[]
。 您丟失了列名和類型信息,但它開箱即用:
CREATE OR REPLACE FUNCTION foo()
RETURNS text[] AS
$func$
SELECT array_agg(result::text) -- cast the record to text!
FROM ( ... ) result
...;
$func$
LANGUAGE sql;
如果您實際上不需要數組,則可以廢棄array_agg()
,返回單個行並使用RETURNS TABLE (...)
聲明返回類型。 搜索plpgsql標簽,你會發現很多例子..
請記住使用以下命令調用設置返回函數:
SELECT * FROM foo();
基於 Erwin's great answer(in the same page) 的小優化:
--create table: create table judgements(id integer, sampleid integer, alterlevel integer, judgements_timestamp timestamp with time zone );
--創建類型:
create type judgements_type as(
ts text, alterlevel int, time_Passed interval
);
完整 function:
create or replace function alarm_event_list
(_sampleid integer,
starttime timestamp without time zone,
stoptime timestamp without time zone)
returns judgements_type[] as
$body$
select array_agg(result::judgements_type) from
(select to_char(judgements_timestamp,'YYYY-MM-DD HH24:MI:SS'),
alterlevel,
coalesce( judgements_timestamp - lag(judgements_timestamp)
over (order by judgements_timestamp), make_interval(0,0,0))
from judgements
where sampleid = _sampleid
and alterlevel > 0
and judgements_timestamp >= starttime
and judgements_timestamp <= stoptime) result;
$body$ language sql;
select * from alarm_event_list(11, '2013-09-17 00:00:00', '2013-09-17 23:59:59');
將返回一個聚合數組。
使其成為 jsonb:
select * from to_jsonb(
alarm_event_list(11, '2013-09-17 00:00:00', '2013-09-17 23:59:59'));
將其設為 2 行,並帶有分隔的 json 文本:
CREATE OR REPLACE FUNCTION public.array_transport(all_items anyarray)
RETURNS SETOF text
LANGUAGE plpgsql
STRICT
AS $function$
declare
item record;
begin
foreach item in array all_items
loop
return next(to_json(item)::text);
end loop;
end;
$function$
然后
select * from array_transport
(alarm_event_list(11, '2013-09-17 00:00:00', '2013-09-17 23:59:59'));
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.