我目前正在为“A”生成一个8字符伪随机大写字符串。。“Z”:

value = ""; 8.times{value  << (65 + rand(25)).chr}

但它看起来不干净,而且不能作为参数传递,因为它不是一个单独的语句。要获取混合大小写字符串“a”。。“z”加“A”。。“Z”,我将其更改为:

value = ""; 8.times{value << ((rand(2)==1?65:97) + rand(25)).chr}

但它看起来像垃圾。

有人有更好的方法吗?


当前回答

使用此方法,您可以传入一个很短的长度。默认设置为6。

def generate_random_string(length=6)
  string = ""
  chars = ("A".."Z").to_a
  length.times do
    string << chars[rand(chars.length-1)]
  end
  string
end

其他回答

我最喜欢的是(:A..:Z).to_A.shuff[0,8].join。请注意,shuffle需要Ruby>1.9。

从Ruby 2.5开始,使用SecureRandom.andlettery非常简单:

len = 8
SecureRandom.alphanumeric(len)
=> "larHSsgL"

它生成包含A-Z、A-Z和0-9的随机字符串,因此应适用于大多数用例。它们是随机安全生成的,这可能也是一个好处。


这是一个基准,用于将其与支持率最高的解决方案进行比较:

require 'benchmark'
require 'securerandom'

len = 10
n = 100_000

Benchmark.bm(12) do |x|
  x.report('SecureRandom') { n.times { SecureRandom.alphanumeric(len) } }
  x.report('rand') do
    o = [('a'..'z'), ('A'..'Z'), (0..9)].map(&:to_a).flatten
    n.times { (0...len).map { o[rand(o.length)] }.join }
  end
end

                   user     system      total        real
SecureRandom   0.429442   0.002746   0.432188 (  0.432705)
rand           0.306650   0.000716   0.307366 (  0.307745)

因此,rand解决方案只需要SecureRandom时间的3/4。如果您生成大量字符串,这可能很重要,但如果您只是时不时地创建一些随机字符串,我会始终使用更安全的实现,因为它也更容易调用,更显式。

为什么不使用SecureRandom?

require 'securerandom'
random_string = SecureRandom.hex

# outputs: 5b5cd0da3121fc53b4bc84d0c8af2e81 (i.e. 32 chars of 0..9, a..f)

SecureRandom还具有以下方法:

基础64随机字节(_B)随机编号

参见:http://ruby-doc.org/stdlib-1.9.2/libdoc/securerandom/rdoc/SecureRandom.html

我不记得我在哪里找到了这个,但对我来说,它似乎是最好的,也是最不需要的过程:

def random_string(length=10)
  chars = 'abcdefghjkmnpqrstuvwxyzABCDEFGHJKLMNPQRSTUVWXYZ0123456789'
  password = ''
  length.times { password << chars[rand(chars.size)] }
  password
end

由3个范围组成的随机字符串的2个解:

(('a'..'z').to_a + ('A'..'Z').to_a + (0..9).to_a).sample(8).join

([*(48..57),*(65..90),*(97..122)]).sample(8).collect(&:chr)*""

每个范围中的一个字符。

如果您需要每个范围中至少一个字符,例如创建一个包含一个大写字母、一个小写字母和一个数字的随机密码,可以执行以下操作:

( ('a'..'z').to_a.sample(8) + ('A'..'Z').to_a.sample(8) + (0..9).to_a.sample(8) ).shuffle.join 
#=> "Kc5zOGtM0H796QgPp8u2Sxo1"