Last active
December 28, 2015 19:09
-
-
Save hchood/7548554 to your computer and use it in GitHub Desktop.
Ruby Fundamentals III - Challenge
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
# Ruby Fundamentals III - Challenge | |
# NOTE: I worked on this with Jonah and then refactored on my own. | |
# METHOD DEFINITIONS | |
def get_input(prompt) | |
puts prompt | |
input = gets.chomp.to_f | |
end | |
def validate_input(input, regex, error_message) | |
while input.to_s.match(regex) | |
puts error_message | |
input = gets.chomp.to_i | |
end | |
input | |
end | |
def valid?(price) | |
if price.match(/\A\d+(\.\d{0,2})?\z/) | |
true | |
end | |
end | |
def calc_subtotals(array) | |
array.each do |hash| | |
hash[:subtotal] = hash[:quantity] * hash[:price] | |
end | |
end | |
def total(array) | |
array = calc_subtotals(array) | |
products = [] | |
array.each {|hash| products << hash[:subtotal]} | |
products.inject(0) {|total, num| total + num} | |
end | |
# INITIALIZED VARIABLES | |
sales = [{type: "Light", price: 5.00, quantity: 0, subtotal: 0}, | |
{type: "Medium", price: 7.50, quantity: 0, subtotal: 0}, | |
{type: "Bold", price: 9.75, quantity: 0, subtotal: 0}] | |
# PROGRAM | |
puts "Welcome to James' coffee emporium!\n\n" | |
puts "1) Add item - $5.00 - Light Bag" | |
puts "2) Add item - $7.50 - Medium Bag" | |
puts "3) Add item - $9.75 - Bold Bag" | |
puts "4) Complete Sale\n\n" | |
# PART 1: gets input (items & quantity sold), puts subtotal | |
while true | |
selection = get_input("Make a selection:").to_i | |
selection = validate_input(selection, /[^1-4]/, "Please enter a selection 1 through 4.") | |
break if selection == 4 | |
quantity = get_input("How many bags:").to_i | |
quantity = validate_input(quantity, /\D/, "Please enter a number.") | |
sales[selection - 1][:quantity] += quantity | |
subtotal = total(sales) | |
puts "Subtotal: $#{sprintf("%.2f", subtotal)}\n\n" | |
end | |
if total(sales) == 0 | |
puts "You did not sell anything. Goodbye!" | |
exit | |
end | |
# PART 2: when finished adding sales, output subtotals & total due | |
puts "\n===Sale Complete===\n\n" | |
sales.each do |item| | |
puts "$#{sprintf("%.2f", item[:subtotal])} - #{item[:quantity]} #{item[:type]}\n" unless item[:subtotal] == 0 | |
end | |
puts "\nTotal: $#{sprintf("%.2f", subtotal)}\n\n" | |
# PART 3: calculates change | |
amount_due = subtotal | |
amount_tendered = get_input("What is the amount tendered?") | |
if valid?(amount_tendered.to_s) | |
amount_tendered = amount_tendered.to_f | |
else | |
puts "WARNING: Invalid currency detected! Exiting..." | |
abort | |
end | |
total_change_due = amount_tendered - amount_due | |
total_change_due_formatted = sprintf("%.2f", total_change_due.abs) | |
if total_change_due >= 0 | |
current_time = Time.now.strftime("%m/%d/%Y %l:%M %p") | |
puts "\n===Thank You!===" | |
puts "The total change due is $#{total_change_due_formatted}" | |
puts | |
puts "#{current_time}" | |
puts "================" | |
else | |
puts "WARNING: Customer still owes $#{total_change_due_formatted}! Exiting..." | |
abort | |
end |
Thanks! I updated it so it works. (I was converting the input I got in my get_input method to an integer, which rounded down the amount_tendered. I changed my get_input method to return a float, and then converted selection & quantity to_i when I called get_input on lines 56 & 60.)
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
I've run this program a few times, and I think Part 3 doesn't correctly calculate change when the amount due isn't a whole dollar value. If I buy 2 of each item, the subtotal is $66.75, but then if the customer pays $66.75, it says the customer still owes $0.75.
On the other hand, the functions at the top are beautiful. Yay for pair refactoring! It's really nice to see how others approached the same problem.