user7055375
user7055375

Reputation:

How do I remove a nil key from my hash?

With Ruby 2.4, I want to count the number of occurrences of an element and store them in a hash. However, I don't want to include any nil keys in my hash. So I tried

my_hash = int_data_col.each_with_object(Hash.new(0)) { |i, h| h[i]+=1 }.delete(nil)

but this returns "1". If I leave off the "delete(nil)", it returns a hash, but then a nil key is included in the hash (assuming a nil was present in the "int_data_col" array). How do I remove the nil key from my hash and still get the correct results?

Upvotes: 3

Views: 2170

Answers (3)

Mark Thomas
Mark Thomas

Reputation: 37517

In Ruby 2.4, there's a way to do it which is very readable:

arr.compact.group_by(&:itself).transform_values(&:size)

Upvotes: 2

donvnielsen
donvnielsen

Reputation: 195

If you want to clean up the array prior to hashing it, then

int_data_col.compact! 
int_data_col.each_with_object(Hash.new(0)) {|i, h| h[i]+=1 }

If you want to simply create the hash, ignoring nil, without disturbing the original array, then the following as suggested by @sagarpandya82

int_data_col.compact.each_with_object(Hash.new(0)) { |i, h| h[i]+=1 }

When you had specified .delete(nil), I think you were expecting it to return the hash with the nil key removed. But what it did was remove the nil key and returned the count value of the nil key (1). From the Hash Class doc, "Deletes the key-value pair and returns the value from hash whose key is equal to key."

Upvotes: 0

Sagar Pandya
Sagar Pandya

Reputation: 9508

Use Array#compact which removes all nil values before the count.

my_hash = int_data_col.compact.each_with_object(Hash.new(0)) { |i, h| h[i]+=1 }

Upvotes: 2

Related Questions