如何在PostgreSQL 9.6和更低版本中改组数组?

Ale*_*ber 2 sql postgresql shuffle plpgsql stored-functions

以下自定义存储功能 -

CREATE OR REPLACE FUNCTION words_shuffle(in_array varchar[])
        RETURNS varchar[] AS
$func$
        SELECT array_agg(letters.x) FROM 
        (SELECT UNNEST(in_array) x ORDER BY RANDOM()) letters;
$func$ LANGUAGE sql STABLE;
Run Code Online (Sandbox Code Playgroud)

在PostgreSQL 9.5.3中改组字符数组:

words=> select words_shuffle(ARRAY['a','b','c','d','e','f']);
 words_shuffle 
---------------
 {c,d,b,a,e,f}
(1 row)
Run Code Online (Sandbox Code Playgroud)

但是现在我切换到PostgreSQL 9.6.2后,该功能停止了工作:

words=> select words_shuffle(ARRAY['a','b','c','d','e','f']);
 words_shuffle 
---------------
 {a,b,c,d,e,f}
(1 row)
Run Code Online (Sandbox Code Playgroud)

可能是因为ORDER BY RANDOM()停止工作:

words=> select unnest(ARRAY['a','b','c','d','e','f']) order by random();
 unnest 
--------
 a
 b
 c
 d
 e
 f
(6 rows)
Run Code Online (Sandbox Code Playgroud)

我正在寻找一个更好的方法来改组字符数组,这可以在新的PostgreSQL 9.6中使用,但也可以在9.5中使用.

我需要它用于开发中的文字游戏,它使用Pl/PgSQL函数.

更新:

汤姆莱恩回复:

现在,在ORDER BY之后扩展目标列表中的SRF.所以ORDER BY正在排序一个虚拟行,然后在此之后发生不必要的行.看到

https://git.postgresql.org/gitweb/?p=postgresql.git&a=commitdiff&h=9118d03a8

kli*_*lin 5

通常,set return函数应放在FROM子句中:

select array_agg(u order by random())
from unnest(array['a','b','c','d','e','f']) u

   array_agg   
---------------
 {d,f,b,e,c,a}
(1 row) 
Run Code Online (Sandbox Code Playgroud)

对于文档(重点添加):

目前,还可以在查询的选择列表中调用返回集的函数.对于查询自身生成的每一行,将调用函数返回集,并为函数结果集的每个元素生成输出行.但请注意,此功能已弃用,可能会在将来的版本中删除.