From: John W Higgins Date: 2009-09-02T02:45:04+09:00 Subject: Re: Nice algorithm for 'spreading' indexes across an array? --00c09f9058e0968db9047287b5a2 Content-Type: text/plain; charset=ISO-8859-1 On Tue, Sep 1, 2009 at 10:11 AM, John W Higgins wrote: > Morning Max, > > On Tue, Sep 1, 2009 at 9:41 AM, Max Williams >wrote: > > > Little ruby algorithm puzzle... > > > > I have a situation where i have an array of 12 items. If someone > > chooses to have n of them (where n can be between 3 and 12) then i want > > to always include the first and last, and then 'spread' the others out > > as evenly as possible between the rest. > > > > So, lets say for the sake of argument that the array holds the numbers 1 > > to 12. > > > > >> arr = (1..12).to_a > > => [1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12] > > > > I would get results back like this > > > > arr.spread(3) > > => [1,6,12] (or [1,7,12], either is fine) > > > > arr.spread(4) > > => [1, 5, 9, 12] (or [1,4,8,12] or [1, 5, 8, 12]) > > > > It feels like there should be a simple solution for this but i can't > > think of a nice way. Anyone? > > > > thanks > > max > > -- > > Posted via http://ww RijndaelManaged< > http://www.ruby-forum.com/> > > w.ruby-forum.com/ . > > > > > So here is my silly attempt - simple but probably not the best performing > answer you will get here. > small correction (should use floor instead of ceil) class Array def spread(members) ret = Array.new #We want sections that total 1 less then the number of members we want back - for example if we #want 3 members in the spread we want 2 equal groups. We use .to_f because we care about fractions here. dist = count.to_f/(members-1) #Now we simply run thru the array and take the members at each spread point. (members-1).times{ |slot| ret << at((slot*dist).floor) } #Add the last member which is always the last member of the array ret << at(-1) end end Also, here is a gist which tends to read better. http://gist.github.com/179241 John --00c09f9058e0968db9047287b5a2--