Programming: Calculate Change for Purchases Under $20

  • Thread starter Thread starter NDiggity
  • Start date Start date
  • Tags Tags
    comp sci
AI Thread Summary
The discussion focuses on programming a solution to calculate change for purchases under $20, specifically addressing issues with handling pennies due to floating-point arithmetic errors. The original code incorrectly calculates the number of pennies due to approximation, leading to incorrect outputs when the change is small. Suggestions include using integer arithmetic by multiplying values by 100 to avoid rounding errors and simplifying the code to improve readability. The conversation also touches on programming shortcuts and the importance of variable types in achieving accurate calculations. Ultimately, the user resolves their issues by implementing these suggestions, leading to correct change calculations.
NDiggity
Messages
53
Reaction score
0

Homework Statement


(Programming) A customer brings purchases worth less than $20 to the till, and hands over a $20 bill. Write a program that prompts a user for the purchase total, then figures out what change the customer should receive -- i.e., how many $10 bills, how many $5 bills, how many toonies ($2), loonies ($1), quarters (0.25), dimes (0.10), nickels (0.05), and pennies (0.01).

The Attempt at a Solution


My only problem is with the pennies part. Here is what I have:

while (change > 0.00) {
change = change - .01;
numberOfPennies = numberOfPennies + 1.;
}

My problem is, let's say the purchases are 19.99. So the change is .01. So my program says how many pennies they should get back. The problem is it says 2. If the purchase is 19.98, it says 3 pennies. What am I doing wrong?
 
Physics news on Phys.org
Can you tell me the variable TYPES and INITIALIZATIONS (if any)?

Perhaps sample code, pasted on rafb.net/paste ?
 
NDiggity said:
What am I doing wrong?
You are using approximate floating-point arithmetic. Therefore, you are getting an approximate answer.
 
Also, you can tidy up your code if you do something like http://rafb.net/p/0yRiIq66.nln.html

You'll save a ton of space (reduce # of lines), and it might be easier to read.
 
Hurkyl said:
You are using approximate floating-point arithmetic. Therefore, you are getting an approximate answer.
Our teachers said if you mix int with float, you will get bad answers. Is this only true with division and multiplication? Also, any other time it deals with pennies its fine, only when the change is strictly pennies does it do this.

One more question. If the input is invalid, I want an error message to pop up and the program to stop. What is the function to stop a program. Sorry, I have only been in this class a month and I have never programmed before. Thank you both so much for your help!
 
Last edited:
If you divide using int/floats, the result value will be truncated.
 
DefaultName said:
If you divide using int/floats, the result value will be truncated.
I changed the numberOfMoney variables all to int and it still says 2 pennies when i say the total cost is 19.99
 
I'm assuming numberOfMoney refers to each of the variables that represent a 10, 5, 1 dollar bills.

If you change those to ints, how are you going to get your change (in cents) to work out? Or am I misinterpreting your post above?
 
  • #10
http://rafb.net/p/KiGOga41.html Try that - that should work.

Notice what I did - there was no need of that while loop when adding up the remaining pennies. Once the change is STRICTLY less than 5 cents, you just add the remainder change (whether it is 4, 3, 2, or 1 cent) to the # of pennies needed.

Also, I don't know if you know, but for shorthand, you can do:

change -= 1; // eq A
change = change - 1; // eq B

eq A and eq B are completely identical, they preform the same mathematical computation. It may seem easier/quicker to type eq A, especially if you are going to be doing things over and over.

x++;

is equivalent to

x = x + 1;

which is also the same as

x += 1;
 
Last edited:
  • #11
Having 0.02, or even 0.0199999998 pennies isn't very useful.




As I was saying, the problem is that you are doing approximate arithmetic. If you want exact answers, you need to either:

(1) Find a way to detect and correct approximation error.
(2) Find a different method that uses only exact arithmetic.
 
  • #12
DefaultName said:
http://rafb.net/p/KiGOga41.html Try that - that should work.

Notice what I did - there was no need of that while loop when adding up the remaining pennies. Once the change is STRICTLY less than 5 cents, you just add the remainder change (whether it is 4, 3, 2, or 1 cent) to the # of pennies needed.

Also, I don't know if you know, but for shorthand, you can do:

change -= 1; // eq A
change = change - 1; // eq B

eq A and eq B are completely identical, they preform the same mathematical computation. It may seem easier/quicker to type eq A, especially if you are going to be doing things over and over.

x++;

is equivalent to

x = x + 1;

which is also the same as

x += 1;

Thank you so much for your help! Also, thank you for teaching me those useful shortcuts, we have not gone over any shortcuts so far in my comp sci classes. Again, thanks for your patience and help!
 
  • #13
My very last question. So for the
if (change <= .05)
numberOfPennies += change;
that gives me numberOfPennies: .01 or something so i just times it by one hundred and it works perfect. But what does that double do at the start instead of float? Without it, I got like 1.0002 pennies, but with it, I get 1 which is what I want.
 
  • #14
It means to use more precision in your floating point numbers.


Incidentally, you don't get 1, even with the doubles; by default, floating point numbers are rounded to 6 decimal digits when printed. Try doing the following:

Add the line
Code:
#include <iomanip>
at the top, and then do your printing with

Code:
cout << "Number of Pennies: " << setprecision(12) << numberOfPennies << endl;
 
  • #15
Hurkyl said:
It means to use more precision in your floating point numbers.


Incidentally, you don't get 1, even with the doubles; by default, floating point numbers are rounded to 6 decimal digits when printed. Try doing the following:

Add the line
Code:
#include <iomanip>
at the top, and then do your printing with

Code:
cout << "Number of Pennies: " << setprecision(12) << numberOfPennies << endl;

Thank you for that, but with that double, for some reason, it only gives me whole numbers for numberOfPennies, which is what i want. So if the change is .01, it says number of pennies: 1. I don't know know, but it works! I'll try your way tho, thank you for your help!
 
  • #16
I just tried it out; a precision of 12 isn't enough to see the error, but 16 is.


I think you misunderstood me, so let me say it again.

You did not get an exact integral number; you only think you did, because when you displayed numberOfPennies, it gets rounded to 6 decimal digits. I wanted you to run it with setprecision so that you can see for yourself that there really is an error there.



Oh, by the way, try entering a purchace price of 19.95...

19.85 is another good one to try...
 
Last edited:
  • #17
NDiggity said:
Thank you so much for your help! Also, thank you for teaching me those useful shortcuts, we have not gone over any shortcuts so far in my comp sci classes. Again, thanks for your patience and help!

Sure, hopefully you'll teacher will notice and be like woah this kid is genius!
 
  • #18
Haha. There is one other problem. If the purchase is like 15.90, instead of getting a dime back, it gives a nickel and 5 pennies...that's correct change, but were supposed to give the smallest amount of coins possible.
 
  • #19
I fixed all the problems! I multipiled all the numbers by 100. That way, a penny is 1 so there is no rounding. Yay! Also, all those useful tips you taught me, we learned them in class today, so they won't think I am some sort of genious :cry: :smile:
 

Similar threads

Replies
4
Views
3K
Replies
6
Views
3K
Replies
2
Views
4K
Replies
80
Views
67K
Back
Top