如何在Ruby中洗牌数组/哈希?
为了学习,这叫什么?正在创建的对象是数组还是哈希如何在Ruby中洗牌数组/哈希?,ruby,shuffle,Ruby,Shuffle,为了学习,这叫什么?正在创建的对象是数组还是哈希 stack_of_cards = [] 我就是这样填的: stack_of_cards << Card.new("A", "Spades", 1) stack_of_cards << Card.new("2", "Spades", 2) stack_of_cards << Card.new("3", "Spades", 3) ... 我想洗牌这个数组/散列中的元素(这叫什么?:S) 有什么建议吗 stack
stack_of_cards = []
我就是这样填的:
stack_of_cards << Card.new("A", "Spades", 1)
stack_of_cards << Card.new("2", "Spades", 2)
stack_of_cards << Card.new("3", "Spades", 3)
...
我想洗牌这个数组/散列中的元素(这叫什么?:S)
有什么建议吗
stack_of_cards.shuffle
它是一个数组,有关详细信息,请参阅
我已经编写了表单,它返回一个新数组,而新数组被洗牌。您可以改为使用:
stack_of_cards.shuffle!
…将数组洗牌到位。此外,还可以使用排序方法:
array.sort {|a, b| rand <=> rand }
array.sort{| a,b | rand}
如果您使用的是未实现
shuffle
的较旧版本的Ruby,那么这可能很有用。与洗牌一样代码>,您可以使用排序
以处理现有数组。如果要洗牌散列,可以使用以下方法:
class Hash
def shuffle
Hash[self.to_a.sample(self.length)]
end
def shuffle!
self.replace(self.shuffle)
end
end
我发布了这个答案,因为如果我搜索“ruby shuffle hash”,我总是会发现这个问题。如果你想发疯并编写你自己的就地shuffle方法,你可以这样做
def shuffle_me(array)
(array.size-1).downto(1) do |i|
j = rand(i+1)
array[i], array[j] = array[j], array[i]
end
array
end
对于阵列:
array.shuffle
[1, 3, 2].shuffle
#=> [3, 1, 2]
对于散列:
Hash[*hash.to_a.shuffle.flatten]
Hash[*{a: 1, b: 2, c: 3}.to_a.shuffle.flatten(1)]
#=> {:b=>2, :c=>3, :a=>1}
#=> {:c=>3, :a=>1, :b=>2}
#=> {:a=>1, :b=>2, :c=>3}
# Also works for hashes containing arrays
Hash[*{a: [1, 2], b: [2, 3], c: [3, 4]}.to_a.shuffle.flatten(1)]
#=> {:b=>2, :c=>3, :a=>1}
#=> {:c=>[3, 4], :a=>[1, 2], :b=>[2, 3]}
如果您想洗牌散列,但不想重载散列类,可以使用sort函数,然后使用to_h函数(Ruby 2.1+)将其转换回散列:
a={“a”=>1,“b”=>2,“c”=>3}
检查
a=a.sort{a,b | rand}.to|h
检查
老问题,但可能对其他人有所帮助。我用它创建了一个纸牌游戏,这就是@davissp14写的,它被称为“Fisher-Yates算法”
现在,您可以将其用作:
numbers_array = [1,2,3,4,5,6,7,8,9]
asnwer = FisherYates.shuffle(numbers_array)
return answer.inspect
对于阵列:
array.shuffle
对于哈希:
hash.sort\u by{rand()}
Word?数组类上实际上有一个shuffle方法?上帝啊但这不会修改数组。供参考:P不管怎样,你编辑了你的答案……看看变更日志,#shuffle似乎是在2006年8月的最后一天添加的,我想这将导致它首次出现在1.8.6中。对于各种Ruby书籍的某些版本来说,这当然太晚了。为了更有趣,还有Array.sample,它从数组中返回一个随机元素。如果您想要3个随机元素,请使用Array.sample(3),“对于各种Ruby书籍的某些版本来说,这肯定太晚了”。非常肯定。Ruby似乎是出版商发展最快的目标之一。我甚至不想谈论寻找好的Rails书籍,因为它们出版时已经过时了。:-)我可以想象你跳过了Struct,但当你有时间的时候,仔细研究一下。这不太管用<代码>[1,2,3]。排序{rand.round}
始终返回[1,2,3]
或[3,2,1]
。正确的方法应该是[1,2,3]。排序{rand}
,或[1,2,3]。按{rand}
排序(如果可以使用洗牌
,请避免)。如果您知道,也可以提及哈希。。。事实上,这是一种非常无效的洗牌方式。排序算法不会对每个元素进行比较。它们隐式地对推论进行编码,如“如果我将A比较为小于B,并且B小于C,那么我可以推断A小于C,而无需检查。”结果严重扭曲,如本文所述(在ObjC中,但同样适用),我要求您删除或更改此答案为什么rand(array.size-1)
而不是rand(array.size)
?rand
不包括在内,因此例如rand(5)
将输出0-4的数字。是的,我以前的实现实际上存在一些问题。我修改了上述方法以反映Knuth Shuffle算法。
a = {"a" => 1, "b" => 2, "c" => 3}
puts a.inspect
a = a.sort {|a, b| rand <=> rand }.to_h
puts a.inspect
module FisherYates
def self.shuffle(numbers)
n = numbers.length
while n > 0
x = rand(n-=1)
numbers[x], numbers[n] = numbers[n], numbers[x]
end
return numbers
end
end
numbers_array = [1,2,3,4,5,6,7,8,9]
asnwer = FisherYates.shuffle(numbers_array)
return answer.inspect