0

I've prepared a method which parses a log file and returns a hash as a result:

  def parse
    @hash = Hash.new { |hash, key| hash[key] = [] }
    File.open(file_path).each do |line|
      customer, product = line.split
      @hash[customer] << product
    end
    @hash
  end

result:

=> {"customer_id$1"=>["product_id$184", "product_id$184", "product_id$94", "product_id$16", 
"product_id$184", "product_id$592"],
"customer_id$3"=>["product_id&16", "product_id&196", "product_id&196", "product_id&82"],
"customer_id$6"=>["product_id$26", "product_id$126", "product_id$26", "product_id$26"]}

How to count all (e.g. customer_id$1 = 6) and unique values (e.g. customer_id$1 = 4) for each customer if they are an array? I'll have this code in AWS lambda so I must use pure Ruby 2.7.

3
  • Enumerable#tally and #select. Commented Dec 1, 2020 at 0:36
  • @ToddA.Jacobs I was thinking about using tally but isn't that function only used for arrays? Commented Dec 1, 2020 at 7:32
  • You need to show your inputs and expected outputs. As written, this seems very much like an X/Y problem, as you can already count unique customers with @hash.keys.count. Commented Dec 1, 2020 at 12:49

2 Answers 2

2

If g is your hash:

h = g.transform_values do |v|
  { nbr_products: v.size, nbr_uniq_products: v.uniq.size }
end
  #=> {"customer_id$1"=>{:nbr_products=>6, :nbr_uniq_products=>4},
  #    "customer_id$3"=>{:nbr_products=>4, :nbr_uniq_products=>3},
  #    "customer_id$6"=>{:nbr_products=>4, :nbr_uniq_products=>2}}

so, for example,

h["customer_id$1"][:nbr_products]
  #=> 6 
h["customer_id$6"][:nbr_uniq_products]
  #=> 2

See Enumerable#transform_values.

Sign up to request clarification or add additional context in comments.

Comments

0

First lets put the result into a variable:

result = {"customer_id$1"=>["product_id$184", "product_id$184", "product_id$94", "product_id$16", 
"product_id$184", "product_id$592"],
"customer_id$3"=>["product_id&16", "product_id&196", "product_id&196", "product_id&82"],
"customer_id$6"=>["product_id$26", "product_id$126", "product_id$26", "product_id$26"]}

Then, we can loop each customer and get the total count and total unique count:

result.each |key, value|
  # total count
  value.size
  # total unique count
  value.uniq.size
end

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.