我有一个数组:
arr1 = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10]
我想将arr1
拆分为x个切片,其中每个切片尽可能完整且相等。
arr2 = arr1.foo(3)
# => [1, 2, 3, 4][5, 6, 7][8, 9, 10]
each_slice
与我想要的完全相反,将数组分成x个元素组。
arr2 = arr1.each_slice(3)
# => [1, 2, 3][4, 5, 6][7, 8, 9][10]
如果可能,我希望不使用像in_groups
这样的特定于轨道的方法来执行此操作。
答案 0 :(得分:6)
class Array
def in_groups(n)
len, rem = count.divmod(n)
(0...n).map { | i | (i < rem) ? self[(len+1) * i, len + 1] : self[len * i + rem, len] }
end
end
答案 1 :(得分:4)
另一种方法:
def in_groups(array, n)
a = array.dup
n.downto(1).map { |i| a.pop(a.size / i) }.reverse
end
arr = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10]
in_groups(arr, 1) #=> [[1, 2, 3, 4, 5, 6, 7, 8, 9, 10]]
in_groups(arr, 2) #=> [[1, 2, 3, 4, 5], [6, 7, 8, 9, 10]]
in_groups(arr, 3) #=> [[1, 2, 3, 4], [5, 6, 7], [8, 9, 10]]
in_groups(arr, 4) #=> [[1, 2, 3], [4, 5, 6], [7, 8], [9, 10]]
in_groups(arr, 5) #=> [[1, 2], [3, 4], [5, 6], [7, 8], [9, 10]]
答案 2 :(得分:3)
你可以使用递归:
def in_groups(arr, n)
return [arr] if n == 1
len = arr.size/n
[arr[0,len]].concat in_groups(arr[len..-1], n-1)
end
arr = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10]
in_groups(arr, 1) #=> [[1, 2, 3, 4, 5, 6, 7, 8, 9, 10]]
in_groups(arr, 2) #=> [[1, 2, 3, 4, 5], [6, 7, 8, 9, 10]]
in_groups(arr, 3) #=> [[1, 2, 3], [4, 5, 6], [7, 8, 9, 10]]
in_groups(arr, 4) #=> [[1, 2], [3, 4], [5, 6, 7], [8, 9, 10]]
in_groups(arr, 5) #=> [[1, 2], [3, 4], [5, 6], [7, 8], [9, 10]]
in_groups(arr, 9) #=> [[1], [2], [3], [4], [5], [6], [7], [8], [9, 10]]
in_groups(arr, 10) #=> [[1], [2], [3], [4], [5], [6], [7], [8], [9], [10]]
in_groups(arr, 11) #=> [[], [1], [2], [3], [4], [5], [6], [7], [8], [9], [10]]
编辑1:首先对于最大的群体,使用.reverse
或用以下代码替换倒数第三行:
len = (arr.size.to_f/n).ceil
编辑2:以下是@ undur的答案的略微变体,对于那些有大脑类型的人来说可能更容易理解&#34; B&#34;和&#34; C&#34;:
class Array
def in_groups(n)
size_small, nbr_large = count.divmod(n)
size_large, nbr_small = size_small+1, n-nbr_large
nbr_for_large = nbr_large * size_large
self[0, nbr_for_large].each_slice(size_large).to_a.concat(
self[nbr_for_large..-1].each_slice(size_small).to_a)
end
end
(1..10).to_a.in_groups(3)
#=> [[1, 2, 3, 4], [5, 6, 7], [8, 9, 10]]