【问题标题】:Create function in PostgreSQL在 PostgreSQL 中创建函数
【发布时间】:2021-11-29 19:47:51
【问题描述】:

我不确定CREATE FUNCTION 语句在 PostgreSQL 中是如何工作的。我想定义一个函数(仅供娱乐),这样给定一个数字 n,它会打印从 1 到 n 的星号 所以我写了这个:

CREATE FUNCTION asterisks(n int)
RETURNS CHAR AS
BEGIN
for i in range(1,n+1):
   print("*"*i + "\n")
END
LANGUAGE python

我想要n=3的结果:

*
**
***

但是,我不确定这样调用 Python 是否可行。我在这里读到 Postgres 支持 Python 作为一种程序语言:

https://www.postgresql.org/docs/current/xplang.html

【问题讨论】:

  • 有 PL/Python,通常用作“不受信任”的版本 (LANGUAGE plpythonu)。请务必阅读当前手册(或您的 Postgres 版本的手册),9.4 已过时。 postgresql.org/docs/current/plpython.htmlLANGUAGE sqlLANGUAGE plpgsql 更常用。 stackoverflow.com/a/24771561/939860您是在询问 PL/Python,还是只是实现您的功能的最佳方式?
  • 谢谢。如果您能给我实现该功能的最佳方法,我将不胜感激。
  • 打印?为什么(以及在哪里)要从 Postgres 打印?!编写一个返回文本的函数。

标签: sql postgresql function plpgsql


【解决方案1】:

Postgres 14 或更高版本

最简单的方法是使用新的标准 SQL 语法:

CREATE OR REPLACE FUNCTION asterisks(n int)
  RETURNS SETOF text
RETURN repeat('*', generate_series (1, n));

或更好(以及所有标准 SQL):

CREATE OR REPLACE FUNCTION asterisks(n int)
  RETURNS SETOF text
  LANGUAGE sql IMMUTABLE STRICT PARALLEL SAFE
BEGIN ATOMIC
SELECT repeat('*', g) FROM generate_series (1, n) g;
END;

“更好”,因为它更容易理解,坚持标准 SQL(更便携)。两者都值得商榷。它适当地设置IMMUTABLE STRICT PARALLEL SAFE,否则默认为VOLATILE CALLED ON NULL INPUT PARALLEL UNSAFE。无可争议。

呼叫:

SELECT asterisks(6);

或者,更明确和符合标准的:

SELECT * FROM asterisks(6);

见:

Postgres 13(或任何版本):

SQL函数:

CREATE OR REPLACE FUNCTION asterisks(n int)
  RETURNS SETOF text
  LANGUAGE sql IMMUTABLE STRICT PARALLEL SAFE AS
$func$
SELECT repeat('*', generate_series (1, n));
$func$;

带有循环的 PL/pgSQL 函数(循环通常更昂贵):

CREATE OR REPLACE FUNCTION pg_temp.asterisks(n int)
  RETURNS SETOF text
  LANGUAGE plpgsql IMMUTABLE STRICT PARALLEL SAFE AS
$func$
BEGIN
FOR i IN 1..n LOOP
   RETURN NEXT repeat('*', i);
END LOOP;
END
$func$;

见:


当然,对于简单的示例,我将只运行普通语句而不是创建函数:

SELECT repeat('*', generate_series (1, 3));

【讨论】:

  • 我以为 OP 期望 SELECT string_agg(repeat('*', g), '\n') FROM generate_series (1, n) g
  • @Bergi:也许吧。看起来 OP 只是想要基本功能的语法模板。
  • 为什么第二种(更详细)的形式比第一种更好?
  • @AdamPiotrowski:好的,“更好”是模糊的。我添加了解释。
猜你喜欢
  • 1970-01-01
  • 2020-07-05
  • 2017-07-14
  • 2017-03-19
  • 1970-01-01
  • 1970-01-01
  • 2012-09-06
  • 2011-06-26
  • 2016-08-03
相关资源
最近更新 更多