#!/usr/bin/env ruby

require "benchmark"
require "bigdecimal"
require "digest/md5"
require "ractorize"

srand(0)

CONCURRENCY = 4
# Is this basically Math::E or related?? And just off a bit due to randomness?
RANDOM_NUMBER_UPPER_BOUND = 2.78
RANDOM_NUMBERS = 10_000.times.map { BigDecimal(rand * RANDOM_NUMBER_UPPER_BOUND) }

class Productizer
  attr_accessor :product, :random_numbers

  def initialize
    self.product = 1
  end

  def generate_random_numbers
    self.random_numbers = 1_000.times.map { BigDecimal(rand * RANDOM_NUMBER_UPPER_BOUND) }
  end

  def multiply_them_all
    random_numbers.each { multiply it }
  end

  def multiply(integer)
    self.product *= integer
  end
end

def do_it(productizer_class)
  productizers = CONCURRENCY.times.map { productizer_class.new }

  productizers.each do |productizer|
    productizer.generate_random_numbers
    productizer.multiply_them_all
  end

  product = productizers.map(&:product).inject(:*)
  puts Digest::MD5.hexdigest(product.to_s)
end

puts Benchmark.measure { do_it(Productizer) }
RactorizedProductizer = Ractorize[Productizer]
puts Benchmark.measure { do_it(RactorizedProductizer) }
puts Benchmark.measure { do_it(RactorizedProductizer) }
puts Benchmark.measure { do_it(Productizer) }
