I'm looking for a method that has the same effect as Python's itertools.product
in Ruby. Take the following Python code:
from itertools import product
chars = []
for i in range(97,123):
chars.append(chr(i))
for a in range(1,3):
for i in product(chars,repeat=a):
s = ''.join(i)
print s
That outputs something like this:
a, b, c... x, y, z, aa, ab, ac... ax, ay, az, ba, bb, bc.. etc.
I tried to translate that into Ruby:
(1..2).each do |n|
('a'..'z').to_a.combination(n).each do |c|
s = c.join
puts s
end
end
But the output isn't the same. The one-character ones work fine (a-z), but when it goes into two-character ones, it doesn't work as I expected:
ab, ac, ad.. ax, ay, az, bc, bd, be
It isn't generating aa
, ba
or bb
- so it appears it's generating all the combinations without repeating characters or something?
So what method should I use to generate all the combinations like itertools.product
does in Python?
I would write (simplified for 3 elements, Ruby 1.9 required):
xs = ["a", "b", "c"]
strings = 1.upto(xs.size).flat_map do |n|
xs.repeated_permutation(n).map(&:join)
end
#=> ["a", "b", "c", "aa", "ab", "ac", ..., "cca", "ccb", "ccc"]
A lazy solution: you could easily write it with each
s instead of map
s, but let's check "lazy" from Ruby 2.0:
xs = ("a".."z").to_a
strings = 1.upto(xs.size).lazy.flat_map do |n|
xs.repeated_permutation(n).lazy.map(&:join)
end
You have Array#product which is like itertools.product.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With