我的目标是编写一个存储过程,它可以将多行中的所有字段值收集到一个单独的输出变量中(可能是varchar(some_length))。它可能看起来很奇怪,但我非常肯定它是我可以在那种情况下使用的唯一一个。我之前没有使用过Firebird,并且存储过程看起来与其他众所周知的数据库系统不同。 我的Firebird是1.5和方言3(不确定它是什么意思)。 所以也许有人可以通过算法示例帮助我。
答案 0 :(得分:5)
以下过程执行您所描述的内容:
SET TERM !!;
CREATE PROCEDURE concat_names
RETURNS (concat VARCHAR(2000))
AS
DECLARE VARIABLE name VARCHAR(100);
BEGIN
concat = '';
FOR SELECT first_name || ' ' || last_name FROM employee INTO :name
DO BEGIN
concat = concat || name || ', ';
END
END!!
SET TERM ;!!
EXECUTE PROCEDURE concat_names;
但我质疑这个解决方案的智慧。你怎么知道VARCHAR足够长到你想要的数据集中的所有行?
运行查询以逐行将结果返回给应用程序会更容易,更安全。每种应用程序编程语言都有连接字符串的方法,但更重要的是,它们有更灵活的方法来管理数据的增长。
顺便说一句,Firebird和InterBase中的“dialect”指的是引入的兼容模式,以便为InterBase 5.x开发的应用程序可以与更高版本的InterBase和Firebird一起使用。这差不多十年前,AFAIK今天没有必要使用低于方言3的任何东西。
答案 1 :(得分:0)
连接时必须测试空值,以下是两个字段的示例以及它们之间的分隔符:
CREATE PROCEDURE CONCAT(
F1 VARCHAR(385),
F2 VARCHAR(385),
SEPARATOR VARCHAR(10))
RETURNS (
RESULT VARCHAR(780))
AS
begin
if ((:f1 is not null) and (:f1 <> '')) then
result = :f1;
if ((:f2 is not null) and (:f2 <> '')) then
if ((result is not null) and (result <> '')) then
begin
if ((:separator is not null) and (separator <> '')) then
result = result||separator||f2;
else
result = result||f2;
end
else
result = f2;
suspend;
end
答案 2 :(得分:0)
使用Firebird存储过程返回多行非常容易。
不要使用:
execute procedure proc_name(value);
而是使用:
select * from proc_name(value);