Today’s Ruby Tuesday in on Array#compact.
Array#compact
operates against a given array and returns a new array with any nil
s removed.
array1 = [1, 2, nil, 3, nil, nil, 4, nil] # => [1, 2, nil, 3, nil, nil, 4, nil] array2 = array1.compact # => [1, 2, 3, 4] array1 # => [1, 2, nil, 3, nil, nil, 4, nil] array2 # => [1, 2, 3, 4] Array.new(7) # => [nil, nil, nil, nil, nil, nil, nil] Array.new(7).compact # => [] [].compact # => [] array_with_no_nils = [1, 2, 3, 4, 5] # => [1, 2, 3, 4, 5] compacted_array_with_no_nils = array_with_no_nils.compact # => [1, 2, 3, 4, 5] compacted_array_with_no_nils # => [1, 2, 3, 4, 5] array_with_no_nils # => [1, 2, 3, 4, 5]
As seen in the examples above, Array#compact
preserves the original order of the elements in the source array.
Array#compact
only performs a shallow removal of any nil
s, and does not remove nil
s from any nested arrays.
mixed_type_array = [nil, :a, nil, nil, "b", [1, 2, nil, 3], nil, :c] # => [nil, :a, nil, nil, "b", [1, 2, nil, 3], nil, :c] mixed_type_array.compact # => [:a, "b", [1, 2, nil, 3], :c]
And because nil
s in Ruby are falsey, we can do a quick sanity check about if Array#compact
is looking at nil
s specifically, or falsey items in general, by creating a new Array filled with false
s and calling compact
on it.
Array.new(9){false}.compact => [false, false, false, false, false, false, false, false, false]
The Array
class also defines Array#compact!, which modifies the underlying state of the Array it is being called on.
array3 = array1.dup # => [1, 2, nil, 3, nil, nil, 4, nil] array4 = array3.compact! # => [1, 2, 3, 4] array3 # => [1, 2, 3, 4] array4 # => [1, 2, 3, 4]
As we can see in the above example, if the array compact!
is being called on does have nil
s in it, the return value is the modified state of the Array.
But if you call Array#compact!
on an array that does not have any nil
s in it, the return value of Array#compact!
is nil
.
Array.new(9){false}.compact! # => nil
–Proctor