I've tried to put results from my vote model in a hash for further usage, but I don't know how to create a hash key from a variable in Ruby. See example below:
def create_hash_array(campaign_votes)
target_hash = Hash.new
campaign_votes.each_with_index do |cv,i|
target_hash[cv.content_id] = {} if i == 0
if target_hash[cv.content_id].member?(cv.vote_button_id)
target_hash[cv.content_id][cv.vote_button_id] = (target_hash[cv.content_id][cv.vote_button_id]).to_i + 1
else
target_hash[cv.content_id] = {cv.vote_button_id => nil}
end
end
target_hash
end
Usually I got an error:
undefined method `member?' for nil:NilClass
but it comes from unrecognized target_hash[cv.content_id]
, how can I make does variable to be recognized target_hash[cv.content_id]
??
I think your code can be boiled down to this:
def create_hash_array(campaign_votes)
target_hash = Hash.new { |h,k| h[k] = Hash.new(0) }
campaign_votes.each do |cv|
target_hash[cv.content_id][cv.vote_button_id] += 1
end
target_hash
end
There's multiple problems here, many to do with getting all tangled up in the process. You initialize the element of the target_hash
structure only on the 0 index position, yet each campaign_vote
could have different content_id
values, meaning you're missing out on those.
This approach creates a single auto-generating Hash that will populate keys with counter hashes, that is hashes defaulting to 0. That means you can always navigate them and += 1
will work because of the default.
This approach is pretty common in Ruby, especially Hash.new(0)
, which is super handy for doing simple counters of arbitrary objects.