Skip to content

Instantly share code, notes, and snippets.

@nandanmen
Created June 23, 2021 16:48
Show Gist options
  • Save nandanmen/a6f52771d2c16ec26bb8d2e762dd9b7f to your computer and use it in GitHub Desktop.
Save nandanmen/a6f52771d2c16ec26bb8d2e762dd9b7f to your computer and use it in GitHub Desktop.
class Wallet
def initialize
@money = 0
end
def add_money!(amount:)
@money += amount
end
def purchase!(amount:)
unless @money >= amount
puts "[Wallet]: Not enough money :( Tried to use $#{amount} but only have $#{@money}"
return false
end
@money -= amount
puts "[Wallet]: Used $#{amount}. Remaining balance: #{@money}"
true
end
end
class GroceryStore
def initialize
@stock = {}
end
def add_stock!(item:, quantity:, price:)
new_stock = { quantity: quantity, price: price }
@stock[item.to_sym] = new_stock
puts "[Store]: Added #{item} to stock with: #{new_stock}"
end
def purchase!(item:, quantity:, wallet:)
puts "[Store]: Purchasing #{quantity} of #{item}..."
unless @stock.key?(item.to_sym)
puts "[Store]: Item #{item} not in stock :("
return
end
stock = @stock[item.to_sym]
unless stock[:quantity] > quantity
puts "[Store]: Not enough stock! Tried to purchase #{quantity} of #{item} but only have #{stock[:quantity]}"
return
end
amount = stock[:price] * quantity
if wallet.purchase!(amount: amount)
new_stock = { quantity: stock[:quantity] - quantity, price: stock[:price] }
@stock[item.to_sym] = new_stock
puts "[Store]: Purchased #{quantity} of #{item}. New stock: #{new_stock}"
end
end
end
# Usage
wallet = Wallet.new
store = GroceryStore.new
store.add_stock!(item: 'apple', quantity: 5, price: 1)
store.add_stock!(item: 'orange', quantity: 10, price: 2)
wallet.add_money!(amount: 10)
# This fails because the store doesn't have enough apples
store.purchase!(item: 'apple', quantity: 10, wallet: wallet)
# This fails because I don't have enough money
store.purchase!(item: 'orange', quantity: 8, wallet: wallet)
# This works!
store.purchase!(item: 'orange', quantity: 3, wallet: wallet)
# Output
# [Store]: Added apple to stock with: {:quantity=>5, :price=>1}
# [Store]: Added orange to stock with: {:quantity=>10, :price=>2}
# [Store]: Purchasing 10 of apple...
# [Store]: Not enough stock! Tried to purchase 10 of apple but only have 5
# [Store]: Purchasing 8 of orange...
# [Wallet]: Not enough money :( Tried to use $16 but only have $10
# [Store]: Purchasing 3 of orange...
# [Wallet]: Used $6. Remaining balance: 4
# [Store]: Purchased 3 of orange. New stock: {:quantity=>7, :price=>2}
@noahkoch
Copy link

For readability, I would suggest not using unless in a multi-line conditional. Generally, in your head, you wind up having to reverse the logic to understand what's it's doing.

So instead of unless stock[:quantity] > quantity you could do if stock[:quantity] <= quantity to give you the same thing. That will read a bit more like English. I find unless reads cleaner when doing a one-liner where the condition is at the end like purchase_item unless out_of_money

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment