Как сгенерировать случайную строку в Ruby
389463 просмотра
30 ответа
В настоящее время я генерирую 8-символьную псевдослучайную строку в верхнем регистре для "A" .. "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}
но это похоже на мусор.
У кого-нибудь есть лучший метод?
Автор: Jeff Источник Размещён: 22.08.2019 04:30Ответы (30)
934 плюса
(0...8).map { (65 + rand(26)).chr }.join
Я провожу слишком много времени в гольфе.
(0...50).map { ('a'..'z').to_a[rand(26)] }.join
И последнее, которое еще более запутанно, но более гибко и тратит меньше циклов:
o = [('a'..'z'), ('A'..'Z')].map(&:to_a).flatten
string = (0...50).map { o[rand(o.length)] }.join
Автор: Kent Fredric
Размещён: 17.09.2008 10:29
776 плюса
Почему бы не использовать SecureRandom?
require 'securerandom'
random_string = SecureRandom.hex
# outputs: 5b5cd0da3121fc53b4bc84d0c8af2e81 (i.e. 32 chars of 0..9, a..f)
SecureRandom также имеет методы для:
- base64
- random_bytes
- случайный номер
см .: http://ruby-doc.org/stdlib-1.9.2/libdoc/securerandom/rdoc/SecureRandom.html
Автор: christopherstyles Размещён: 25.10.2009 12:32244 плюса
Я использую это для генерации случайных URL-дружественных строк с гарантированной максимальной длиной:
rand(36**length).to_s(36)
Он генерирует случайные строки из строчных букв az и 0-9. Это не очень настраиваемый, но он короткий и чистый.
Автор: Christoffer Möller Размещён: 26.08.2010 07:34169 плюса
Это решение генерирует строку легко читаемых символов для кодов активации; Я не хотел, чтобы люди путали 8 с B, 1 с I, 0 с O, L с 1 и т. Д.
# Generates a random string from a set of easily readable characters
def generate_activation_code(size = 6)
charset = %w{ 2 3 4 6 7 9 A C D E F G H J K M N P Q R T V W X Y Z}
(0...size).map{ charset.to_a[rand(charset.size)] }.join
end
Автор: ImNotQuiteJack
Размещён: 29.01.2009 08:20
127 плюса
Другие упоминали что-то похожее, но при этом используется функция безопасного URL.
require 'securerandom'
p SecureRandom.urlsafe_base64(5) #=> "UtM7aa8"
p SecureRandom.urlsafe_base64 #=> "UZLdOkzop70Ddx-IJR0ABg"
p SecureRandom.urlsafe_base64(nil, true) #=> "i0XQ-7gglIsHGV2_BNPrdQ=="
Результат может содержать AZ, az, 0-9, «-» и «_». «=» Также используется, если отступ равен true.
Автор: Travis Reeder Размещён: 28.08.2011 06:2150 плюса
С ruby 2.5 действительно легко с SecureRandom.alphanumeric
:
len = 8
SecureRandom.alphanumeric(len)
=> "larHSsgL"
Создает случайные строки, содержащие AZ, az и 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
решение занимает всего около 3/4 времени SecureRandom
. Может иметь значение, если вы генерируете действительно много строк, но если вы просто время от времени создаете какую-то случайную строку, я всегда выбираю более безопасную реализацию (так как ее также проще вызывать и более явную).
47 плюса
[*('A'..'Z')].sample(8).join
Генерация случайной 8-буквенной строки (например, NVAYXHGR)
([*('A'..'Z'),*('0'..'9')]-%w(0 1 I O)).sample(8).join
Генерация случайной 8-символьной строки (например, 3PH4SWF2), исключая 0/1 / I / O. Рубин 1.9
Автор: Shai Coleman Размещён: 04.01.2012 04:4130 плюса
Я не могу вспомнить, где я нашел это, но мне кажется, что это лучший и наименее интенсивный процесс:
def random_string(length=10)
chars = 'abcdefghjkmnpqrstuvwxyzABCDEFGHJKLMNPQRSTUVWXYZ0123456789'
password = ''
length.times { password << chars[rand(chars.size)] }
password
end
Автор: Travis Reeder
Размещён: 12.07.2009 09:40
27 плюса
25 плюса
Если вы хотите строку указанной длины, используйте:
require 'securerandom'
randomstring = SecureRandom.hex(n)
Он сгенерирует случайную строку длины, 2n
содержащую 0-9
иa-f
13 плюса
Array.new(n){[*"0".."9"].sample}.join
где n = 8 в вашем случае.
Обобщено: Array.new(n){[*"A".."Z", *"0".."9"].sample}.join
и т. Д. - из этого ответа
11 плюса
require 'sha1'
srand
seed = "--#{rand(10000)}--#{Time.now}--"
Digest::SHA1.hexdigest(seed)[0,8]
Автор: Coren
Размещён: 17.09.2008 10:40
10 плюса
Вот один строчный код для случайной строки длиной 8
random_string = ('0'..'z').to_a.shuffle.first(8).join
Вы также можете использовать его для случайного пароля длиной 8
random_password = ('0'..'z').to_a.shuffle.first(8).join
Я надеюсь, что это поможет и удивительно.
Автор: Awais Размещён: 19.11.2014 06:1210 плюса
Ruby 1.9+:
ALPHABET = ('a'..'z').to_a
#=> ["a", "b", "c", "d", "e", "f", "g", "h", "i", "j", "k", "l", "m", "n", "o", "p", "q", "r", "s", "t", "u", "v", "w", "x", "y", "z"]
10.times.map { ALPHABET.sample }.join
#=> "stkbssowre"
# or
10.times.inject('') { |s| s + ALPHABET.sample }
#=> "fdgvacnxhc"
Автор: Ragmaanir
Размещён: 24.07.2010 09:04
8 плюса
Вот один простой код для случайного пароля с длиной 8
rand_password=('0'..'z').to_a.shuffle.first(8).join
Надеюсь, это поможет.
Автор: Thaha kp Размещён: 15.10.2012 06:518 плюса
Помните: rand
предсказуемо для злоумышленника и, следовательно, вероятно, небезопасно. Вы обязательно должны использовать SecureRandom, если это для генерации паролей. Я использую что-то вроде этого:
length = 10
characters = ('A'..'Z').to_a + ('a'..'z').to_a + ('0'..'9').to_a
password = SecureRandom.random_bytes(length).each_char.map do |char|
characters[(char.ord % characters.length)]
end.join
Автор: pencil
Размещён: 30.03.2013 02:30
6 плюса
Еще один метод, который мне нравится использовать
rand(2**256).to_s(36)[0..7]
Добавьте ljust, если вы действительно параноик по поводу правильной длины строки:
rand(2**256).to_s(36).ljust(8,'a')[0..7]
Автор: user163365
Размещён: 08.01.2010 11:17
6 плюса
SecureRandom.base64(15).tr('+/=lIO0', 'pqrsxyz')
Что-то от Devise
Автор: Thorpe Obazee Размещён: 19.04.2012 12:255 плюса
Я думаю, что это хороший баланс краткости, ясности и простоты модификации.
characters = ('a'..'z').to_a + ('A'..'Z').to_a
# Prior to 1.9, use .choice, not .sample
(0..8).map{characters.sample}.join
Легко модифицируется
Например, включая цифры:
characters = ('a'..'z').to_a + ('A'..'Z').to_a + (0..9).to_a
Прописные шестнадцатеричные:
characters = ('A'..'F').to_a + (0..9).to_a
Для действительно впечатляющего множества персонажей:
characters = (32..126).to_a.pack('U*').chars.to_a
Автор: Nathan Long
Размещён: 20.06.2011 01:48
5 плюса
Просто добавив мои центы здесь ...
def random_string(length = 8)
rand(32**length).to_s(32)
end
Автор: pduersteler
Размещён: 27.05.2012 10:27
5 плюса
Вы можете использовать String#random
из граней Ruby Gem facets
:
это в основном делает это:
class String
def self.random(len=32, character_set = ["A".."Z", "a".."z", "0".."9"])
characters = character_set.map { |i| i.to_a }.flatten
characters_len = characters.length
(0...len).map{ characters[rand(characters_len)] }.join
end
end
Автор: Tilo
Размещён: 22.08.2014 10:53
4 плюса
Мой любимый это (:A..:Z).to_a.shuffle[0,8].join
. Обратите внимание, что для перемешивания требуется Ruby> 1,9.
4 плюса
Это решение нуждается во внешней зависимости, но кажется более привлекательным, чем другое.
- Установите gem faker
Faker::Lorem.characters(10) # => "ang9cbhoa8"
4 плюса
Дано:
chars = [*('a'..'z'),*('0'..'9')].flatten
Одно выражение, которое может быть передано в качестве аргумента, допускает дублирование символов:
Array.new(len) { chars.sample }.join
Автор: Tim James
Размещён: 20.04.2011 07:58
3 плюса
Недавно я делал что-то подобное, чтобы сгенерировать 8-байтовую случайную строку из 62 символов. Символы были 0-9, az, AZ. У меня был их массив, так как я делал 8 циклов и выбирал случайное значение из массива. Это было внутри приложения рельсов.
str = ''
8.times {|i| str << ARRAY_OF_POSSIBLE_VALUES[rand(SIZE_OF_ARRAY_OF_POSSIBLE_VALUES)] }
Странно то, что я получил много дубликатов. Теперь случайно это почти никогда не должно происходить. 62 ^ 8 огромен, но из 1200 или около того кодов в БД у меня было много дубликатов. Я заметил, что они происходят на часовых границах друг друга. Другими словами, я мог бы увидеть дуплет в 12:12:23 и 2:12:22 или что-то в этом роде ... не уверен, является ли время проблемой или нет.
Этот код был в до создания объекта activerecord. Перед созданием записи этот код запускается и генерирует «уникальный» код. Записи в БД всегда создавались надежно, но код (стр. В строке выше) дублировался слишком часто.
Я создал сценарий для выполнения 100000 итераций этой строки с небольшой задержкой, поэтому потребуется 3-4 часа в надежде увидеть какой-то повторяющийся шаблон на почасовой основе, но ничего не увидел. Я понятия не имею, почему это происходило в моем приложении rails.
Автор: erik Размещён: 07.08.2010 08:163 плюса
3 плюса
Мои 2 цента:
def token(length=16)
chars = [*('A'..'Z'), *('a'..'z'), *(0..9)]
(0..length).map {chars.sample}.join
end
Автор: tybro0103
Размещён: 03.05.2012 03:49
3 плюса
Я просто пишу маленький гем random_token
для генерации случайных токенов для большинства случаев использования, наслаждайтесь ~
https://github.com/sibevin/random_token
Автор: Sibevin Wang Размещён: 03.12.2013 04:013 плюса
2 решения для случайной строки, состоящей из 3 диапазонов:
(('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"
Автор: peter
Размещён: 10.02.2012 08:50
2 плюса
С помощью этого метода вы можете пройти в произвольной длине. По умолчанию установлено значение 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
Автор: Ryan Bigg
Размещён: 18.09.2008 12:53
Вопросы из категории :
- ruby Вызов команд оболочки из Ruby
- ruby Почему в Ruby нет реального StringBuffer или StringIO?
- ruby Как создать случайный 10-значный номер в рубине?
- ruby Каков наилучший способ конвертировать массив в хеш в Ruby
- ruby Determine file type in Ruby
- ruby Раскладка каталога для чистого Ruby-проекта
- random Случайное целое число в VB.NET
- random Как запросить случайную строку в SQL?
- random Как сгенерировать случайную буквенно-цифровую строку?
- random Выберите N случайных элементов из списка <T> в C #
- random Генерирование (псевдо) случайных буквенно-цифровых строк
- passwords Отключить функцию браузера «Сохранить пароль»
- passwords Генерация случайных паролей
- passwords Как сгенерировать случайную строку в Ruby
- passwords Нужно ли вводить максимальную длину для паролей?
- passwords Какая хорошая альтернатива секретным вопросам?
- passwords Как удалить ключевую фразу для ключа SSH без необходимости создания нового ключа?