Division of an array into equal parts in a ruby

I need a way to split an array into a bunch of arrays in another array of equal size. Does anyone have a way to do this?

for example

a = [0, 1, 2, 3, 4, 5, 6, 7] a.method_i_need(3) a.inspect => [[0,1,2], [3,4,5], [6,7]] 
+47
arrays ruby ruby-on-rails
Sep 11 '12 at 17:09
source share
5 answers

Are you looking for Enumerable#each_slice

 a = [0, 1, 2, 3, 4, 5, 6, 7] a.each_slice(3) # => #<Enumerator: [0, 1, 2, 3, 4, 5, 6, 7]:each_slice(3)> a.each_slice(3).to_a # => [[0, 1, 2], [3, 4, 5], [6, 7]] 
+101
Sep 11 '12 at 17:12
source share

Perhaps I misunderstand the question, since another answer has already been accepted, but it sounded like you wanted to divide the array into 3 equal groups, regardless of the size of each group, and not divide it into N groups of 3, as in the previous answers. If this is what you are looking for, Rails (ActiveSupport) also has an in_groups method:

 a = [0,1,2,3,4,5,6] a.in_groups(2) # => [[0,1,2,3],[4,5,6,nil]] a.in_groups(3, false) # => [[0,1,2],[3,4], [5,6]] 

I don't think there is an equivalent to ruby, however you can get roughly the same results by adding this simple method:

 class Array; def in_groups(num_groups) return [] if num_groups == 0 slice_size = (self.size/Float(num_groups)).ceil groups = self.each_slice(slice_size).to_a end; end a.in_groups(3) # => [[0,1,2], [3,4,5], [6]] 

The only difference (as you can see) is that this will not spread the “empty space” in all groups; each group, but the last is equal in size, and the last group always contains the remainder plus all the "empty space".

Update: As @rimsky pointed out, the above method does not always result in the correct number of groups (sometimes it creates several “empty groups” at the end and leaves them). Here's an updated version, reduced from an ActiveSupport definition , that extends to additional data to fill in the requested number of groups.

 def in_groups(number) group_size = size / number leftovers = size % number groups = [] start = 0 number.times do |index| length = group_size + (leftovers > 0 && leftovers > index ? 1 : 0) groups << slice(start, length) start += length end groups end 
+89
Nov 29
source share

Try

 a.in_groups_of(3,false) 

He will do your work

+13
Sep 11 '12 at 17:12
source share

As mltsy wrote, in_groups(n, false) should do the job.

I just wanted to add a little trick to get the correct balance my_array.in_group(my_array.size.quo(max_size).ceil, false) .

Here is an example to illustrate this trick:

 a = (0..8).to_a a.in_groups(4, false) => [[0, 1, 2], [3, 4], [5, 6], [7, 8]] a.in_groups(a.size.quo(4).ceil, false) => [[0, 1, 2], [3, 4, 5], [6, 7, 8]] 
0
Mar 10 '17 at 14:47
source share

To do this, you need to be a little smarter to soak the extra pieces, but this is a reasonable start.

 def i_need(bits, r) c = r.count (1..bits - 1).map { |i| r.shift((c + i) * 1.0 / bits ) } + [r] end > i_need(2, [1, 3, 5, 7, 2, 4, 6, 8]) => [[1, 3, 5, 7], [2, 4, 6, 8]] > i_need(3, [1, 3, 5, 7, 2, 4, 6, 8]) => [[1, 3, 5], [7, 2, 4], [6, 8]] > i_need(5, [1, 3, 5, 7, 2, 4, 6, 8]) => [[1, 3], [5, 7], [2, 4], [6], [8]] 
0
Nov 06 '17 at 9:41 on
source share



All Articles