Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

sorting a ruby array of objects by an attribute that could be nil

I have an array of objects that I need to sort by a position attribute that could be an integer or nil, and I need the objects that have the nil position to be at the end of the array. Now, I can force the position to return some value rather than nil so that the array.sort doesn't fail, but if I use 0 as this default, then it puts those objects at the front of the sort. What's the best way to to do this sort? should I just set the nil values to some ridiculously high number that is 'almost' always guaranteed to be at the end? or is there some other way i could cause the array.sort method to put the nil attribute objects at the end of the array? the code looks like this:

class Parent   def sorted_children      children.sort{|a, b| a.position <=> b.position}   end end  class Child   def position     category ? category.position : #what should the else be??   end end 

now, if i make the 'else' something like 1000000000, then it's most likely gonna put them at the end of the array, but I don't like this solution as it's arbitrary

like image 928
Chris Drappier Avatar asked Apr 30 '09 18:04

Chris Drappier


People also ask

How do you sort an array of objects in Ruby?

You can use the sort method on an array, hash, or another Enumerable object & you'll get the default sorting behavior (sort based on <=> operator) You can use sort with a block, and two block arguments, to define how one object is different than another (block should return 1, 0, or -1)

Is empty array nil in Ruby?

nil? will only return true if the object itself is nil. That means that an empty string is NOT nil and an empty array is NOT nil. Neither is something that is false nil. => NilClassnil.

How do you get rid of nil in Ruby?

When you want to remove nil elements from a Ruby array, you can use two methods: compact or compact! . They both remove nil elements, but compact! removes them permanently. In this shot, we will be talking about the compact!

What sorting algorithm does Ruby use?

The Array#sort method in Ruby uses the venerable Quicksort algorithm. In its best case, Quicksort has time complexity O(n log n), but in cases where the data to be sorted is already ordered, the complexity can grow to O(n2).


1 Answers

I would just tweak your sort to put nil items last. Try something like this.

foo = [nil, -3, 100, 4, 6, nil, 4, nil, 23]  foo.sort { |a,b| a && b ? a <=> b : a ? -1 : 1 }  => [-3, 4, 4, 6, 23, 100, nil, nil, nil] 

That says: if a and b are both non-nil sort them normally but if one of them is nil, return a status that sorts that one larger.

like image 194
glenra Avatar answered Oct 13 '22 22:10

glenra