Snippet: Shuffle an Array

Posted by kev Tue, 20 Mar 2007 07:47:00 GMT

class Array
  def shuffle
    sort { rand(3) - 1 }
  end
end

arr = (1..10).to_a
# => [1, 2, 3, 4, 5, 6, 7, 8, 9, 10]
arr.shuffle
# => [1, 8, 6, 10, 9, 3, 7, 2, 5, 4]
arr.shuffle
# => [3, 7, 10, 4, 5, 8, 2, 6, 9, 1]

Posted in , ,  | 7 comments

Comments

  1. Avatar Eric said about 1 hour later:

    Very impressive… Well done!

  2. Avatar Patrick Ritchie said about 5 hours later:

    Cool! I read this before my morning coffee and had to run the following to figure it out:

    >> rand(3) – 1 => 0 >> rand(3) – 1 => -1 >> rand(3) – 1 => 1

  3. Avatar Eric said about 6 hours later:

    One possible application:

    n=10
    a=[“Je t’aime”,”I love you”,”Ti amo”,”Ich liebe dich”]*n
    puts a.shuffle.join(”-”)

  4. Avatar Stephen Waits said about 9 hours later:

    Hey Kev,

    We had a long discussion about this in Dec ‘05:

    http://groups.google.com/group/comp.lang.ruby/browse_frm/thread/ee661599c4da36ee?tvc=1&q=steve%40waits.net+ruby+shuffle

    —Steve

  5. Avatar Stephen Waits said about 9 hours later:

    The crux of it is that your way is pretty slow, by a factor of 4x or 5x when compared to..

    arr.sort_by {rand}

    I managed to beat sort_by{rand} by a hair with:

    def shuffle3 h = Hash.new self.each { |v| h[rand(1000000000)] = v } h.keys.sort.collect { |k| h[k] } end

    However, the cleanliness of sort_by{rand} cannot be denied.

    Also, you may add these to Enumerable too.

    —Steve

  6. Avatar Stephen Waits said about 9 hours later:

    Bah.. formatting broke on that. You get the idea. —Steve

  7. Avatar Shane said 13 days later:

    Killer, I love this stuff!

Comments are disabled