所以这个问题的评论提到,PostgreSQL中的“存储过程”和“存储函数”略有不同。
评论链接到维基百科文章,但其中一些似乎并不适用(例如,它们可以在SELECT
声明中使用)。
语法本身似乎有点混乱:
CREATE FUNCTION emp_stamp() RETURNS trigger AS $emp_stamp$
BEGIN
[...]
END;
$emp_stamp$ LANGUAGE plpgsql;
CREATE TRIGGER emp_stamp BEFORE INSERT OR UPDATE ON emp
FOR EACH ROW EXECUTE PROCEDURE emp_stamp();
您创建 aFUNCTION
但将其称为PROCEDURE
.
那么这两者有什么区别呢?
正式来说,PostgreSQL 只有“函数”。触发函数有时被称为“触发过程”,但这种用法没有明确的含义。在内部,函数有时被称为过程,例如在系统目录中
pg_proc
。这是 PostQUEL 的保留。某些人(可能有不同数据库系统经验)可能与过程相关联的任何特性,例如它们与防止 SQL 注入或使用输出参数的相关性,也适用于 PostgreSQL 中存在的函数。现在,当 PostgreSQL 社区中的人们谈论“存储过程”或“真正的存储过程”时,他们通常指的是类函数对象的假设特性,可以在其主体中启动和停止事务,这是当前函数无法做到的做。在此上下文中使用术语“存储过程”似乎与其他数据库产品类似。有关模糊的想法,请参阅此邮件列表线程。
然而,在实践中,函数与过程在事务控制能力方面的这种区别并没有被普遍接受,当然,许多没有数据库偏见的程序员会将类似于 Pascal 的过程解释为没有返回值的函数。(SQL 标准似乎采取了中间立场,因为默认情况下过程具有与函数不同的事务行为,但这可以针对每个对象进行调整。)所以无论如何,尤其是在查看 Stack Exchange 上的问题时非常复杂的受众,您应该避免过多假设并使用更清晰的术语或定义您期望的属性。
PostgreSQL 11 添加了存储过程作为新的模式对象。您可以使用该
CREATE PROCEDURE
语句创建一个新过程。存储过程在以下方面不同于函数:
存储过程不必返回任何内容,使用
INOUT
参数时只返回一行。您可以在存储过程中提交和回滚事务,但不能在函数中。
CALL
您使用语句而不是语句来执行存储过程SELECT
。与函数不同,过程不能嵌套在其他 DDL 命令 (
SELECT
,INSERT
,UPDATE
,DELETE
) 中。在 DDL 方面,Postgres 没有过程对象,只有函数。Postgres 函数可以返回值或 void,因此它们在其他 RDBMS 中扮演函数和过程的角色。中的“过程”
create trigger
一词指的是一个功能。在 Postgres 文档中,“过程”也是称为函数的数据库对象的同义词,例如:“使用 CREATE FUNCTION 命令创建触发器过程”。
触发器“过程”确实有特定的规则:它们必须声明为不带参数且返回类型为 trigger 的函数。这里的例子。
术语“存储过程”和“存储函数”在 PostgreSQL 中可以互换使用,并且通常被认为是同一个意思。其他数据库可能会区分过程和函数(很像 VB 如何区分子例程和函数)。
只要 PostgreSQL 中的函数返回类似于表的内容,您就可以像使用标准表一样使用该函数的输出。
CREATE TRIGGER
语法有点混乱,但我怀疑它可能在 ANSI 标准最终确定之前就已经到位。我只有一个 SQL:2003 的副本,所以我只能推测为什么这个命名法很奇怪。TL;DR 版本:在 PostgreSQL 中,“过程”等同于“功能”。
简短的回答是函数返回一个值,但过程没有。
这种区别存在于为 SQL 1992 提出的持久存储模块 (SQL/PSM) 中。我不知道 SQL/PSM 是否曾将其纳入标准。
在 MSSQL 中,存储过程是一组预编译的 sql 命令。
用户定义的函数有多种形式。根据编写的函数类型,函数:一个存储过程:
从抽象概念层面比较接受的答案,我理解功能和输入/输出角度的区别。下面我用 sp 和 f 分别表示存储过程和函数。
在表达式中使用: sp 不能在表达式中使用,而函数可以,这意味着您可以在其他语句中使用来自 af 的返回值,例如
返回值:sp不会自动返回值,除非你指定refcursor返回类型,打开并返回一个游标;f 返回嵌入“return”子句的最后一个语句中的结果,例如select子句。
返回单个/多个结果集:这里的结果集是指格式可能不同的结果列表,例如单个整数、文本数组和两个表的集合。sp 可以返回多个集合,只要指定 refcursor 返回类型,打开并返回一个游标。但是, f 只能返回一种类型的集合。
通常,存储过程用于修改不需要返回值的数据库数据或结构,如删除、更新、删除等;或需要多个结果集的情况。另一方面,函数主要用于普通查询。
有关我的解释的更多详细信息,请参阅此链接:PostgreSQL 中的存储过程和函数