在PostgreSQL中生成随机字符串

时间:2016-04-10 17:58:33

标签: sql postgresql postgresql-9.3

我使用此SQL查询在PostgreSQL中生成随机值

chr(ascii('B') + (random() * 25)::integer)

如何使用相同的查询生成15个字符随机字符串?

8 个答案:

答案 0 :(得分:5)

这是我的贡献

postgres=# SELECT array_to_string(array(select substr('ABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789',((random()*(36-1)+1)::integer),1) from generate_series(1,50)),'');
                  array_to_string                   
----------------------------------------------------
 4XOS6TQG5JORLF3D1RPXUWR2FQKON9HIXV0UGH0CQFT1LN5D4L
(1 row)

它允许您指定允许的字符集和字符串的长度。

答案 1 :(得分:4)

另一种很容易阅读的解决方案(性能应该合理,但未执行基准测试):

select substr(md5(random()::text), 0, 25);

如果愿意,可以大写:

select upper(substr(md5(random()::text), 0, 25));

答案 2 :(得分:3)

这将为您提供一个长度为15的随机单词,其中包含在源值常量

中配置的字母
select
  string_agg(substr(characters, (random() * length(characters) + 1)::integer, 1), '') as random_word
from (values('ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789')) as symbols(characters)
  -- length of word
  join generate_series(1, 15) on 1 = 1

编辑:要获得多个随机单词,您可以使用以下内容:

with symbols(characters) as (VALUES ('ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789'))
select string_agg(substr(characters, (random() * length(characters) + 1) :: INTEGER, 1), '')
from symbols
join generate_series(1,8) as word(chr_idx) on 1 = 1 -- word length
join generate_series(1,10000) as words(idx) on 1 = 1 -- # of words
group by idx

答案 3 :(得分:3)

是的,也可以通过单一查询来做到这一点,但是如果你想要每个字符都应该根据范围分开,那么上面是解决方案

SELECT array_to_string(ARRAY(
            SELECT chr((ascii('B') + round(random() * 25)) :: integer) 
            FROM generate_series(1,15)), 
             '');

答案 4 :(得分:2)

这是一个想法:

select (chr(ascii('B') + (random() * 25)::integer) ||
        chr(ascii('B') + (random() * 25)::integer) ||
        chr(ascii('B') + (random() * 25)::integer) ||
        chr(ascii('B') + (random() * 25)::integer) ||
        chr(ascii('B') + (random() * 25)::integer) ||
        chr(ascii('B') + (random() * 25)::integer) ||
        chr(ascii('B') + (random() * 25)::integer) ||
        chr(ascii('B') + (random() * 25)::integer) ||
        chr(ascii('B') + (random() * 25)::integer) ||
        chr(ascii('B') + (random() * 25)::integer) ||
        chr(ascii('B') + (random() * 25)::integer) ||
        chr(ascii('B') + (random() * 25)::integer) ||
        chr(ascii('B') + (random() * 25)::integer) ||
        chr(ascii('B') + (random() * 25)::integer) ||
        chr(ascii('B') + (random() * 25)::integer) 
       ) as Random15

答案 5 :(得分:1)

我尝试使用@Bennit 的解决方案 但注意到了一些缺陷。随机部分的计算有点错误,导致错误的结果:结果长度与预期不同(短)。

[快速浏览@lyndon-s 版本 - 很可能它也有同样的缺点]

所以这是@bennit版本的更新版本:

select
string_agg(substr(characters, (random() * length(characters) + 0.5)::integer, 1), '') as random_word
from (values('ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789')) as symbols(characters)
-- length of word
join generate_series(1, 15) on 1 = 1

这里演示了为什么需要更改:

更正:

select n,count(*) from (
select (random() * 10 + 0.5)::integer as n from dbfiles
join generate_series(1, 100000) on 1 = 1
) as s group by n
order by 1;

原文:

select n,count(*) from (
select (random() * 10 + 1)::integer as n from dbfiles
join generate_series(1, 100000) on 1 = 1
) as s group by n
order by 1;

答案 6 :(得分:0)

把我的 2c 扔在这里。我需要随机字符串来做一些基准测试,所以对我来说真正重要的是这些字符串彼此之间是唯一的。

select rpad(generate_series::varchar, 1000, 'hi') from generate_series(1,10);

rpad - 向右填充直到长度(1000),用 'hi' 填充 generate_series(1,10) - 生成 10 行

结合上面的答案,您也可以这样做:

select rpad(generate_series::varchar, 1000, md5(random()::text)) from generate_series(1,10)

这确保您有 200 个字符,或者任何所需的长度。

答案 7 :(得分:0)

那么递归 CTE 怎么样。结合生成系列以获得您想要的任意数量。

with recursive brs(rstg, n) as 
     ( select chr(ascii('B') + (random() * 25)::integer), 1
         from generate_series(1,50)    --- or however many you want
       union all 
       select rstg || chr(ascii('B') + (random() * 25)::integer), n+1
         from brs 
        where n<= 15 
     )
select rstg 
  from brs
 where n=15;
相关问题