在Ruby中将数组数组合并到只有前向的所有可能组合中

Tra*_*vis 28 ruby arrays combinations unique

我有一个数组数组,如下所示:

[['1','2'],['a','b'],['x','y']]
Run Code Online (Sandbox Code Playgroud)

我需要将这些数组组合成一个字符串,其中包含所有三个集合的所有可能组合,仅向前.我已经看到很多关于任何顺序的所有可能组合的例子,这不是我想要的.例如,我不希望第一组中的任何元素出现在第二组之后,或者第三组中的任何元素出现在第一组或第二组之前,依此类推.因此,对于上面的示例,输出将是:

['1ax', '1ay', '1bx', '1by', '2ax', '2ay', '2bx', '2by']
Run Code Online (Sandbox Code Playgroud)

数组的数量和每组的长度是动态的.

有人知道如何在Ruby中解决这个问题吗?

And*_*imm 56

知道你的Array#product:

a = [['1','2'],['a','b'],['x','y']]
a.first.product(*a[1..-1]).map(&:join)
Run Code Online (Sandbox Code Playgroud)

  • 另外请注意,您可以执行以下操作:`first,* rest = * a; combos = first.product(* rest).map(&:join)`; 恕我直言,这条额外的行比`* a [1 ..- 1]`的可读性有所提高。 (2认同)

Phr*_*ogz 8

使用递归的,所谓的"动态编程"方法解决:

  • 对于n阵列,将第一个阵列的条目与剩余(n-1)个阵列上的每个结果组合
  • 对于单个数组,答案就是那个数组

在代码中:

def variations(a)
  first = a.first
  if a.length==1 then
    first
  else
    rest = variations(a[1..-1])
    first.map{ |x| rest.map{ |y| "#{x}#{y}" } }.flatten
  end
end

p variations([['1','2'],['a','b'],['x','y']])
#=> ["1ax", "1ay", "1bx", "1by", "2ax", "2ay", "2bx", "2by"]

puts variations([%w[a b],%w[M N],['-'],%w[x y z],%w[0 1 2]]).join(' ')
#=> aM-x0 aM-x1 aM-x2 aM-y0 aM-y1 aM-y2 aM-z0 aM-z1 aM-z2 aN-x0 aN-x1 aN-x2
#=> aN-y0 aN-y1 aN-y2 aN-z0 aN-z1 aN-z2 bM-x0 bM-x1 bM-x2 bM-y0 bM-y1 bM-y2
#=> bM-z0 bM-z1 bM-z2 bN-x0 bN-x1 bN-x2 bN-y0 bN-y1 bN-y2 bN-z0 bN-z1 bN-z2
Run Code Online (Sandbox Code Playgroud)

你也可以颠倒逻辑,小心你应该能够非递归地实现这个.但递归答案相当简单.:)


小智 5

纯、减同积:

a = [['1','2'],['a','b'],['x','y']]
a.reduce() { |acc, n| acc.product(n).map(&:flatten) }.map(&:join)
#  => ["1ax", "1ay", "1bx", "1by", "2ax", "2ay", "2bx", "2by"]
Run Code Online (Sandbox Code Playgroud)