0

I have a problem with this loop and I don't understand where the error is and why it goes to infinite loop.

I need to determine the amount of change to be returned to the customer by the cashier and display the change using the smallest possible number of coins of 1, 2, 5, 10, 20 and 50 cents.

In theory I seem to have reasoned well, in fact the first 2 operations are correct but, I think, it goes into infinite loop when it has to choose a coin of 0.05. If anyone can explain to me where I am going wrong I will be grateful.

In my while loop, the idea is to take the copy of the tot_rest and compare it to the for loop of the coins. If tot_rest_temp is greater than the coin, then it sums the coin in rest_temp and subtracts it from tot_rest_temp.

I do rest_coin.append(m) to see how many and what kind of coins it gave in rest.

coin = [0.50, 0.20, 0.10, 0.05, 0.02, 0.01]
payment = 1.00
product_cost = 0.23

tot_rest = round(payment - product_cost,2) 
print("Resto: ", round(tot_rest,2))

rest_coin = []
resto_temp = float(round(0,2))                  #  sum of coins  
tot_rest_temp = round(tot_rest,2)               #  copy the tot_rest 

while payment != (tot_rest + resto_temp):
    for m in coin:
        # print("1 tot resto temp: ",tot_resto_temp)
        if tot_rest_temp > m:
            resto_temp += m
            rest_coin.append(m)
            tot_rest_temp -= m
            print("m: ",m)
            print("resto temp: ",resto_temp)
            print("tot resto temp: ",tot_rest_temp)
            continue
        else:
            break
            
print("Final resto temp",resto_temp)
print("Final coins",rest_coin)

I tried using Decimal but the problem remains. So I decided to put everything in centimals, thinking it would solve it. Instead the problem gives the same result.

coin = [50, 20, 10, 5, 2, 1]
payment = 100
product_cost = 23

I used abs(payment != abs(tot_rest + rest_temp)):

but that doesn't solve either. Also:

payment > (tot_rest + rest_temp): 

gives the same problem, the only thing that changes is that it prints me:

Final rest_temp 70
Final coins [50, 20]

At this point I have no more ideas to solve, I am still a beginner in programming. If anyone has any ideas--Thanks

Prectux
  • 1
  • 3
  • I'd put money on the fact that you're dealing with floating point values causing this problem. Try printing the two things you're comparing in the `while` statement, `payment`, and `tot_rest + resto_temp`. I bet you're getting wonky floating point errors. – ddejohn Jul 01 '22 at 04:10
  • 1
    I concur that the use of binary floating-point values is likely the cause of the problem. For currency, I would recommend using fixed-point [Decimal](https://docs.python.org/3/library/decimal.html) values with a precision of 2, instead, assuming you have the option to do so. – Schol-R-LEA Jul 01 '22 at 04:17
  • 1
    Integral numbers of cents is also a good option, and a fair bit easier than `Decimal`. – Blckknght Jul 01 '22 at 04:26
  • for Schol-R-LEA: Yes I had started using Decimal, but I wanted to do this exercise without importing any type of form. If there is no other solution I will eventually have to import it. – Prectux Jul 01 '22 at 12:20
  • However, even putting everything in cents (i.e.: 100, 50, 20... etc.) the loop goes into infinite loop, so there is something wrong with the logic I used. Also using: while abs(paymnt != abs(tot_resto + resto_temp)): – Prectux Jul 01 '22 at 21:31

1 Answers1

-1

Floating point math can be really broken in Python. Instead of using !=, try >. Your while loop would be while payment > (tot_rest + resto_temp):

  • This works, but strangely the values (5, 2 and 1) skips them and shows in coins only [50, 20]. Final resto temp 70 - Final coins [50, 20] – Prectux Jul 01 '22 at 21:36