gpt4 book ai didi

postgresql - 虚拟化 SQL 函数中的列

转载 作者:行者123 更新时间:2023-11-29 14:36:17 28 4
gpt4 key购买 nike

我正在尝试弄清楚是否可以创建一个 SQL 函数,将参数行视为“鸭子类型”。也就是说,我希望能够传递来自具有某些公共(public)列名的不同表或 View 的行,并在函数内对这些列进行操作。

这里有一个非常简单的例子来尝试描述这个问题:

=> CREATE TABLE tab1 (
id SERIAL PRIMARY KEY,
has_desc BOOLEAN,
x1 TEXT,
description TEXT
);
CREATE TABLE
=> CREATE FUNCTION get_desc(tab tab1) RETURNS TEXT AS $$
SELECT CASE tab.has_desc
WHEN True THEN
tab.description
ELSE
'Default Description'
END;
$$ LANGUAGE SQL;

=> INSERT INTO tab1 (has_desc, x1, description) VALUES (True, 'Foo', 'FooDesc');
INSERT 0 1
=> INSERT INTO tab1 (has_desc, x1, description) VALUES (True, 'Bar', 'BarDesc');
INSERT 0 1
=> SELECT get_desc(tab1) FROM tab1;
get_desc
----------
BarDesc
FooDesc
(2 rows)

这当然是很做作的。实际上,我的表有更多的字段,功能也比那复杂得多。

现在我想添加其他表/ View 并将它们传递给同一个函数。新表/ View 具有不同的列,但函数将关心的列对所有这些列都是通用的。为了添加到这个简单的示例中,我添加了这两个表:

CREATE TABLE tab2 (
id SERIAL PRIMARY KEY,
has_desc BOOLEAN,
x2 TEXT,
description TEXT
);
CREATE TABLE tab3 (
id SERIAL PRIMARY KEY,
has_desc BOOLEAN,
x3 TEXT,
description TEXT
);

请注意,这三个都有 has_descdescription 字段,它们是 get_desc 中实际使用的唯一字段。但是当然,如​​果我尝试将现有函数与 tab2 一起使用,我会得到:

=> select get_desc(tab2) FROM tab2;
ERROR: function get_desc(tab2) does not exist
LINE 1: select get_desc(tab2) FROM tab2;
^
HINT: No function matches the given name and argument types. You might need to add explicit type casts.

我希望能够定义一个通用函数,它与 get_desc 做同样的事情,但将三个表中的任何一个的行作为参数。有什么办法吗?

或者是否有某种方法可以将整行转换为仅包含一组已定义字段的通用行类型?

(我意识到我可以将函数参数更改为只采用 XX.has_descXX.description 但我试图隔离函数内部使用的字段无需在调用函数的每个地方扩展它们。)

最佳答案

您可以 create a cast:

CREATE CAST (tab2 AS tab1) WITH INOUT;

INSERT INTO tab2 (has_desc, x2, description) VALUES (True, 'Bar', 'From Tab2');

SELECT get_desc(tab2::tab1) FROM tab2;

get_desc
-----------
From Tab2
(1 row)

关于postgresql - 虚拟化 SQL 函数中的列,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/44209481/

28 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com