I've got some Ruby code here, that works, but I'm certain I'm not doing it as efficiently as I can.
I have an Array of Objects, along this line:
[
{ name: "foo1", location: "new york" },
{ name: "foo2", location: "new york" },
{ name: "foo3", location: "new york" },
{ name: "bar1", location: "new york" },
{ name: "bar2", location: "new york" },
{ name: "bar3", location: "new york" },
{ name: "baz1", location: "chicago" },
{ name: "baz2", location: "chicago" },
{ name: "baz3", location: "chicago" },
{ name: "quux1", location: "chicago" },
{ name: "quux2", location: "chicago" },
{ name: "quux3", location: "chicago" }
]
I want to create some number of groups - say 3 - where each group contains a semi-equal amount of items, but interspersed by location
.
I tried something like this:
group_size = 3
groups = []
group_size.times do
groups.push([])
end
i = 0
objects.each do |object|
groups[i].push(object)
if i < (group_size - 1)
i += 1
else
i = 0
end
end
This returns a groups
object, that looks like:
[
[{:name=>"foo1", :location=>"new york"},
{:name=>"bar1", :location=>"new york"},
{:name=>"baz1", :location=>"chicago"},
{:name=>"quux1", :location=>"chicago"}],
[{:name=>"foo2", :location=>"new york"},
{:name=>"bar2", :location=>"new york"},
{:name=>"baz2", :location=>"chicago"},
{:name=>"quux2", :location=>"chicago"}],
[{:name=>"foo3", :location=>"new york"},
{:name=>"bar3", :location=>"new york"},
{:name=>"baz3", :location=>"chicago"},
{:name=>"quux3", :location=>"chicago"}]
]
So you can see there's a couple of objects from each location in each grouping.
I played around with each_slice()
and group_by()
, even tried to use inject([])
- but I couldn't figure out a more elegant method to do this.
I'm hoping it's something that I'm overlooking - and I need to account for more location
s and a non-even number of Objects.
Yes, this bookkeeping with
i
is usually a sign there should be something better. I came up with:because I like the cycle method.