请帮助我在ruby中的“shuffle”代码

时间:2010-11-12 10:13:54

标签: ruby shuffle

这是问题

  

洗牌。现在你已经完成了   新的排序算法,怎么样   相反?写一个shuffle方法   采取数组并完全返回   洗牌版。一如既往,你会   想要测试它,但测试这个   比较棘手:你怎么测试   确定你得到了完美   洗牌?你甚至会说什么?   完美的洗牌会是什么?现在测试   它

这是我的代码答案:

def shuffle arr
    x = arr.length
while x != 0
        new_arr = []
    rand_arr = (rand(x))
    x--
    new_arr.push rand_arr
    arr.pop rand_arr
end

new_arr

end

puts (shuffle ([1,2,3]))

我的错误是什么?为什么这段代码不起作用?

6 个答案:

答案 0 :(得分:2)

这是一个更加Rubyish版本:

class Array
  def shuffle!
    size.downto(1) { |n| push delete_at(rand(n)) }
    self
  end
end

puts [1,2,3].shuffle!

答案 1 :(得分:2)

这是一种更简洁的写作方式:

def shuffle(arr)
  new_arr = []

  while (arr.any?) do 
    new_arr << arr.delete_at(rand(arr.length))
  end

  new_arr
end

还有一些测试:

5.times do
  puts shuffle((1..5).to_a).join(',')
end

>> 4,2,1,3,5
>> 3,2,1,4,5
>> 4,2,5,1,3
>> 5,2,1,4,3
>> 4,3,1,5,2

答案 2 :(得分:1)

您的索引与您的值混淆了。当您执行new_arr.push rand_arr时,您将所提出的任意随机索引作为new_arr末尾的值。您打算做的是new_arr.push arr[rand_arr],其中arr[rand_arr]rand_arr中索引arr的值。

答案 3 :(得分:1)

除了轻微的其他错误之外,您似乎无法理解pop和push正在做什么(从数组末尾获取或添加一些项目)。

您可能正在尝试编写类似下面的内容。

def shuffle arr
    x = arr.length
    new_arr = []
    while x != 0
        randpos = rand(x)
        x = x-1
        item = arr[randpos]
        new_arr.push item
        arr[randpos] = arr[x]
        arr.pop
    end

    new_arr

end

puts (shuffle ([1,2,3]))

答案 4 :(得分:0)

Ruby 1.8.7和1.9.2有一个内置的Array #shuffle方法。

答案 5 :(得分:0)

马克·托马斯答案的变体。由于删除操作性能,他的算法对于大型数组来说可能非常慢。

class Array
  def shuffle!
    size.downto(1) do |n|
       index=rand(n)
       # swap elements at index and the end
       self[index], self[size-1] = self[size-1],self[index]
    end
    self
  end
end

puts [1,2,3].shuffle!

此算法为O(大小),而Mark的算法为O(大小为^ 2)。在我的计算机上,Mark的答案需要400秒才能在我的机器上洗涤1,000,000个元素,而使用我的方法则为0.5秒。