我的交叉表查询(见下文)运行得很好。但是,我必须生成大量此类查询,而且 - 至关重要的是 - 列定义的数量每天都会有所不同。如果输出columndef的数量与交叉表的第二个参数的数量不匹配,则交叉表将抛出错误并中止。因此,我不能像在当前查询中那样“硬连接”列定义,而是需要一个能够确保列定义即时同步的函数。是否有可能编写一个可在所有这些实例中重用的通用postgres函数?这是我的疑问:
SELECT *
FROM crosstab
('SELECT
to_char(ipstimestamp, ''mon DD HH24h'') As row_name,
ips.objectid::text As category,
COUNT(*)::integer As value
FROM loggingdb_ips_boolean As log
INNER JOIN IpsObjects As ips
ON log.Varid=ips.ObjectId
WHERE (( log.varid = 37551)
OR (log.varid = 27087)
OR (log.varid = 29469)
OR (log.varid = 50876)
OR (log.varid = 45096)
OR (log.varid = 54708)
OR (log.varid = 47475)
OR (log.varid = 54606)
OR (log.varid = 25528)
OR (log.varid = 54729))
GROUP BY to_char(ipstimestamp, ''yyyy MM DD HH24h''), row_name, objectid, category
ORDER BY to_char(ipstimestamp, ''yyyy MM DD HH24h''), row_name, objectid, category',
'SELECT DISTINCT varid
FROM loggingdb_ips_boolean ORDER BY 1;'
)
As CountsPerHour(row_name text,
"25528" integer,
"27087" integer,
"29469" integer,
"37551" integer,
"45096" integer,
"54606" integer,
"54708" integer,
"54729" integer)
PS:请注意,此查询可以针对以下服务器上的测试数据运行: 主持人:bellariastrasse.com 数据库:IpsLogging 用户:来宾 密码:来宾
答案 0 :(得分:2)
我担心你想要的东西不是完全可能的。如果返回类型不同,您可以
SETOF record
。但是,您必须在每次通话时提供列定义列表 - 将您带回到您开始的位置。
但这就是你要避免的......
如果你必须编写“大量此类查询”,你可以使用查询生成器函数,它不会返回结果,而是返回你将在一秒内执行的DDL脚本步。基本上是一个函数,它将变量部分作为参数并在您的示例中生成查询字符串。RETURNS text
。
这可能变得相当复杂。必须考虑彼此之上的几个元级别,但这绝对是可能的。请务必大量使用dollar-quoting以防止引用疯狂。