random strings 2

Posted by Steven Soroka Fri, 22 Feb 2008 00:24:00 GMT

Over a year ago, I posted about generating random strings.  After juggling the problem around with people who knew more ruby than I, we had collectively come up with this:

  (1..4).map{(0..?z).map(&:chr).grep(/[a-z\d]/i)[rand(62)]}.join

A visitor named Evan posted a shorter solution, which was based on sorting the string randomly and using a regular expression to pull it out all at once:

  ((9..?z).map(&:chr).sort_by{rand}*”)[/[a-z\d]{4}/i] 

There was only one problem with it.  On rare occasion it would return nil because it couldn’t find enough characters in a-zA-Z0-9 next to each other.  Hmm.  Big problem.  A year and two months later I set out to see if I couldn’t use a combination of the two ideas to better shorten the solution. This time I wanted 6 random characters, but that doesn’t really change the code.

by adopting the *” instead of .join trick I save two characters.  by re-writing it completely I can save one more and end up with this:

  ((0..?z).map(&:chr).sort_by{rand}.grep(/\w/)*”)[/[^_]{6}/]

the idea here is that we’re making a randomly sorted string, stripping non word characters, joining, then removing the pesky _ and grabbing 6 characters at the same time. Since we’ve removed non-word characters, we’ll always find at least 6 together in a group. yay!  So the record stands at 59 characters for a random string of only a set of [a-zA-Z0-9]. 

Trackbacks

Use the following link to trackback from your own site:
http://blog.stevensoroka.ca/trackbacks?article_id=60

Comments

Leave a comment

  1. Avatar
    coderrr 8 months later:

    (0..9).map{0until(c=rand(?z).chr)=~/(?!_)\w/;c}*''

    50 chars

  2. Avatar
    Magnus Holm 8 months later:

    (0..9).map{rand(?z).chr[/[^_\W]/]||redo}*”

    42 chars (for generating a 10-length random string) :-)

Comments