N.A
N.A

Reputation: 311

Ruby Type Error: no implicit conversion of Symbol into Integer

rideshare_data = {
  DR0001: [
    {
      DATE: "02_03_2016",
      COST: 10,
      RIDER_ID: "RD0003",
      RATING: 3
    },
    {
      DATE: "02_03_2016",
      COST: 30,
      RIDER_ID: "RD0015",
      RATING: 4
    },
    {
      DATE: "02_05_2016",
      COST: 45,
      RIDER_ID: "RD0003",
      RATING: 2
    }
  ],
  DR0002: [
    {
      DATE: "02_03_2016",
      COST: 25,
      RIDER_ID: "RD0073",
      RATING: 5
    },
    {
      DATE: "02_04_2016",
      COST: 15,
      RIDER_ID: "RD0013",
      RATING: 1
    },
    {
      DATE: "02_5_2016",
      COST: 35,
      RIDER_ID: "RD0066",
      RATING: 3
    }
  ]
}

rideshare_data.each do |driver_id, driver_data|
  money_earned = 0
  driver_data.each do |rides|
    rides.each do |ride, ride_data|
      money_earned = [ride_data][:COST].reduce(:+)
      puts "#{driver_id} earned #{money_earned} total"
    end
  end
end

So I have a dataset of arrays and hashes, and I am trying to find the total money earned for each driver by summing the :COST keys. No matter what I try in the last block, I get the error no implicit conversion of Symbol/Hash/String into Integer. Help would be appreciated!

Upvotes: 0

Views: 6894

Answers (1)

Sebastián Palma
Sebastián Palma

Reputation: 33420

Since you're using [] on an array, Ruby expects you to pass an integer, as arrays can only be accessed by their index, and that's why it returns such error.

no implicit conversion of Symbol into Integer (TypeError)

The result of [ride_data], gives you a string within an array, so, you don't have the ability to pass a symbol, accessing a key as if it'd be a Hash object.

As your rideshare_data is a hash, containing different values for each key (driver id), you can just iterate over each key values and get the value of each COST key, and do the operation you need:

rideshare_data.each_with_object([]) do |(key, value), array|
  array << "#{key} earned #{value.sum { |ride| ride[:COST] }} total"
end.each { |total| puts total } 

# DR0001 earned 85 total
# DR0002 earned 75 total

There you iterate over each value in rideshare_data, using an initial empty array as a memo where to store your data, with sum, you collect each value for COST keys and sum them. The each on the final is just to show each value within the resulting array.

Depending on your Ruby version, you might need map and sum instead just sum (value.map { |ride| ride[:COST] }.sum).

Upvotes: 3

Related Questions