# Thread: Why does this fail?

1. ## Why does this fail?

I have tried in vain to debug this. The logic seems to fail around dimes. For most of the values I put in, the logic works fine. However sometimes, there will be a "penny" left in difference and other times there will be a negative number. Any ideas how this happens?

Code:
```#include <iostream>
#include <string>
using namespace std;

int main()
{
// self documenting code begin
cout << "This program calculates the amount of change\ngiven back after a purchase";
// self documening code end
cout << "\nEnter the purchase amount:  ";
double purchase;
cin >> purchase;
cout << "\nEnter the amount of money given:  ";
double money;
cin >> money;
double difference = money - purchase;
double change = difference;
int dollar = 1;
double halfDollar = .5;
double quarter = .25;
double dime = .1;
double nickel = .05;
double penny = .01;
for (int dollars = 0; difference >= 1; dollars++)
{
cout << difference <<"  DEBUGGING LOGIC - subtracting a dollar\n"; // for debugging
difference = difference - dollar;
cout << difference <<"  DEBUGGING LOGIC - I subtracted a dollar\n"; // for debugging
}
for (int halfDollars = 0; difference >= 0.50; halfDollars++)
{
cout << difference <<"  DEBUGGING LOGIC - subtracting a half dollar\n"; // for debugging
difference = difference - halfDollar;
cout << difference <<"  DEBUGGING LOGIC - I subtracted a half dollar\n"; // for debugging
}
for (int quarters = 0; difference >= 0.25; quarters++)
{
cout << difference <<"  DEBUGGING LOGIC - subtracting a quarter\n"; // for debugging
difference = difference - quarter;
cout << difference <<"  DEBUGGING LOGIC - I subtracted a quarter\n"; // for debugging
}
for (int dimes = 0; difference >= 0.10; dimes++)
{
cout << difference <<"  DEBUGGING LOGIC! - subtracting a dime\n"; // for debugging
difference = difference - dime;
cout << difference <<"  DEBUGGING LOGIC - I subtracted a dime\n"; // for debugging
}
for (int nickels = 0; difference >= 0.05; nickels++)
{
cout << difference <<"  DEBUGGING LOGIC - subtracting a nickel\n"; // for debugging
difference = difference - nickel;
cout << difference <<"  DEBUGGING LOGIC - I subtracted a nickel\n"; // for debugging
}
for (int pennies = 0; difference > 0.01; pennies++)
{
cout << difference <<"  DEBUGGING LOGIC! - subtracting a penny\n"; // for debugging
difference = difference - penny;
cout << difference <<"  DEBUGGING LOGIC - I subtracted a penny\n"; // for debugging
}
if (difference > 0.01)
{
cout << difference <<"  DEBUGGING LOGIC! - Added a penny to make it right?\n"; // for debugging
++pennies;
}
if (difference < 0)
{
cout << difference <<"  DEBUGGING LOGIC! - Subtracted a penny to make it right?\n"; // for debugging
--pennies;
}

// Self documenting output to screen
cout << difference <<"  THE END RESULT OF DIFFERENCE DEBUGGING LOGIC!\n"; // for debugging
cout << "\nPlease give the customer "  << change << " back in change\n";
cout <<  dollars << " dollars\n";
cout <<  halfDollars << " half dollars\n";
cout <<  quarters << " quarters\n";
cout <<  dimes << " dimes\n";
cout <<  nickels << " nickels\n";
cout <<  pennies << " pennies\n";
cin.ignore();
return 0;
}``` 2. Try doing it using an integer counting the number of cents, not a double containing the fractions of a dollar. 3. I picke up your code and changed some stuff. Please try:
Code:
```#include <iostream>
#include <string>
using namespace std;

int main()
{
double dollar = 1;
double halfDollar = .5;
double quarter = .25;
double dime = .1;
double nickel = .05;
double penny = .01;

double purchase;
double money;
double change;
double difference;

do {
cout << "This program calculates the amount of difference\ngiven back after a purchase";
cout << "\nEnter the purchase amount:  ";
cin >> purchase;
cout << "\nEnter the amount of money given:  ";
cin >> money;
change = difference = money - purchase;

if (difference<0) { cout << "You'll loose money if the client pays less than the good's price...\n\n"; }

} while (difference<0);

int dollars = 0;
for (; difference >= dollar; dollars++)
{
cout << difference <<"  DEBUGGING LOGIC - subtracting a dollar\n"; // for debugging
difference -= dollar;
cout << difference <<"  DEBUGGING LOGIC - I subtracted a dollar\n"; // for debugging
}

int halfDollars = 0;
for (; difference >= halfDollar; halfDollars++)
{
cout << difference <<"  DEBUGGING LOGIC - subtracting a half dollar\n"; // for debugging
difference -= halfDollar;
cout << difference <<"  DEBUGGING LOGIC - I subtracted a half dollar\n"; // for debugging
}

int quarters = 0;
for (; difference >= quarter; quarters++)
{
cout << difference <<"  DEBUGGING LOGIC - subtracting a quarter\n"; // for debugging
difference -= quarter;
cout << difference <<"  DEBUGGING LOGIC - I subtracted a quarter\n"; // for debugging
}

int dimes = 0;
for (; difference >= dime; dimes++)
{
cout << difference <<"  DEBUGGING LOGIC! - subtracting a dime\n"; // for debugging
difference -= dime;
cout << difference <<"  DEBUGGING LOGIC - I subtracted a dime\n"; // for debugging
}

int nickels = 0;
for (; difference >= nickel; nickels++)
{
cout << difference <<"  DEBUGGING LOGIC - subtracting a nickel\n"; // for debugging
difference -= nickel;
cout << difference <<"  DEBUGGING LOGIC - I subtracted a nickel\n"; // for debugging
}

int pennies = 0;
for (; difference > penny; pennies++)
{
cout << difference <<"  DEBUGGING LOGIC! - subtracting a penny\n"; // for debugging
difference -= penny;
cout << difference <<"  DEBUGGING LOGIC - I subtracted a penny\n"; // for debugging
}

if (difference > penny)
{
cout << difference <<"  DEBUGGING LOGIC! - Added a penny to make it right?\n"; // for debugging
++pennies;
}

if (difference < 0)
{
cout << difference <<"  DEBUGGING LOGIC! - Subtracted a penny to make it right?\n"; // for debugging
--pennies;
}

// Self documenting output to screen
cout << difference <<"  THE END RESULT OF DIFFERENCE DEBUGGING LOGIC!\n"; // for debugging
cout << "\nPlease give the customer "  << change << " back in change\n";
cout <<  dollars << " dollars\n";
cout <<  halfDollars << " half dollars\n";
cout <<  quarters << " quarters\n";
cout <<  dimes << " dimes\n";
cout <<  nickels << " nickels\n";
cout <<  pennies << " pennies\n";
cin.ignore();
return 0;
}```
Now i'll point somethings i changed:

• changed the declaration of dollar variable to be double as well because of the later calculations.
• put the part where you ask for input in a while loop to prevent you from having negative change.
• Notice the -= operator, x -= y; does the exacte same thing as x = x - y;
• changed the for statements because if you want to access the variables at the end of the program you must declare the variables outside the for statement. Added to that i removed the assignment to such variable as i assign it the required value on the line before (initializing a variable to some value is less expensive than initializing and later assignment i've heard)
• I decided it would be better to use the defined value of the dollar,halfDollar, etc... values for the change computations instead of using hardcoded values like you had.
Anyway, this might not be perfect but from what i've tried at least it runs and seems to do what you're after. Don't just take the code and use it without ever looking at it again, try to see why i've changed what i've changed and see if you can learn with it, that's the purpose of me posting the code.

Hope this has helped somewhat. Cheers 4. <EDIT: this applies to original code only>
It doesn't compile. The reason is that all the variables you declare in your for() loops are local in scope to the loop; yet you try to use them at the end of the program.

For another thing, using doubles for dollar amounts seems to be a Really Bad Idea™ to me. It's probably the reason your pennies part is fouling up.

The thing is, doubles can't represent 1/100 ie the cent values accurately. More or less accurate to, say, 0.00000000001017.

You *could* deal with complicated stuff like EPSILON, or make your own USDollar class or something, OR simply read in entire lines with getline(), get the numbers out of it and store them as seperate dollar/cent values. 5. The thing is, doubles can't represent 1/100 ie the cent values accurately.
doubles are accurate to DBL_DIG digits (defined in <float.h>). DBL_DIG is usually 15. .0001 requires far less than 15 digits to store (if your dollar value is small).

I usually store monetary values in an int, multiplying "12.34" by 100 and storing it as "1234". 6. Originally Posted by me!
You *could* deal with complicated stuff like EPSILON, or make your own USDollar class or something
Example:
Code:
```#include <iostream>
#include <string>
#include <sstream>

class usdollar
{
friend usdollar operator-(usdollar);
friend std::ostream &operator<<(std::ostream&, usdollar);
friend std::istream &operator<<(std::istream&, usdollar&);
friend bool operator>(usdollar, usdollar);
friend bool operator<(usdollar, usdollar);
friend bool operator==(usdollar, usdollar);
friend usdollar operator+(usdollar, usdollar);
friend usdollar operator-(usdollar, usdollar);
friend usdollar operator*(usdollar, double);
friend usdollar operator/(usdollar, double);

protected:
int dollaramount;
int centamount;
int sign;

public:
//variables

//constructors
usdollar(double amount)
{
this -> init(amount);
}
usdollar(int dollars = 0, int cents = 0)
{
this -> init(dollars, cents);
}
//various assignment operators
//all return itself for use in chained expressions
usdollar operator=(usdollar u1)
{
this -> dollaramount = u1.dollaramount;
this -> centamount = u1.centamount;
this -> sign = u1.sign;
return *this;
}
//dirty-work functions
void init(double amount)
{
//we take EPSILON to be 1e-9 here, should be enough
this -> init((int)amount, (int)((amount + 0.000000001 - (int)amount) * 100));
}
void init(int dollars = 0, int cents = 0)
{
this -> sign = 1;
this -> dollaramount = dollars;
this -> centamount = cents;
}
void rationalize()
{
this -> dollaramount += this -> centamount / 100;
this -> centamount %= 100;

while(this -> centamount < 0)
{
this -> dollaramount--;
this -> centamount += 100;
}

if(this -> dollaramount < 0)
{
this -> sign *= -1;
this -> dollaramount = -this -> dollaramount;
this -> centamount = -this -> centamount;

this -> rationalize();
}
}

//return double value
double getd()
{
return this -> sign * (this -> dollaramount + this -> centamount / 100.0);
}
//return sign
int gsign()
{
return this -> sign;
}
};
//unary minus
usdollar operator-(usdollar u1)
{
u1.sign *= -1;
return u1;
}

//input and output operators
std::istream &operator>>(std::istream &in, usdollar &u1)
{
double temp;
in >> temp;

u1.init(temp);
return in;
}
std::ostream &operator<<(std::ostream &out, usdollar u1)
{
if(u1.sign == -1)
{
out << "-";
}
out << "\$" << u1.dollaramount << ".";
if(u1.centamount < 10)
{
out << "0";
}
out << u1.centamount;
return out;
}
//larger than?
bool operator>(usdollar u1, usdollar u2)
{
//compare dollaramounts first
if(u1.dollaramount > u2.dollaramount)
{
return true;
}
if(u1.dollaramount < u2.dollaramount)
{
return false;
}
//dollaramounts are eqaul, compare centamounts
if(u1.centamount > u2.centamount)
{
return true;
}
if(u1.centamount <= u2.centamount)
{
return false;
}
}
//smaller than?
bool operator<(usdollar u1, usdollar u2)
{
//compare dollaramounts first
if(u1.dollaramount < u2.dollaramount)
{
return true;
}
if(u1.dollaramount > u2.dollaramount)
{
return false;
}
//dollaramounts are eqaul, compare centamounts
if(u1.centamount < u2.centamount)
{
return true;
}
if(u1.centamount >= u2.centamount)
{
return false;
}
}
//equality
//unneeded (compiler provides default), but given anyway
bool operator==(usdollar u1, usdollar u2)
{
return ((u1.dollaramount == u2.dollaramount) && (u1.centamount == u2.centamount));
}
usdollar operator+(usdollar u1, usdollar u2)
{
u1.dollaramount += u2.dollaramount;
u1.centamount += u2.centamount;
//rationalize
u1.rationalize();
return u1;
}
//subtraction
usdollar operator-(usdollar u1, usdollar u2)
{
u1.dollaramount -= u2.dollaramount;
u1.centamount -= u2.centamount;
//rationalize
u1.rationalize();
return u1;
}
//and...
usdollar operator*(usdollar u1, double n)
{
//rationalize
u1.init(u1.sign * (u1.dollaramount + u1.centamount / 100.0) * n);
return u1;
}
usdollar operator/(usdollar u1, double n)
{
//rationalize
u1.init(u1.sign * (u1.dollaramount + u1.centamount / 100.0) / n);
return u1;
}
//complex operators
//reuse previous operators
bool operator>=(usdollar u1, usdollar u2)
{
return ((u1 > u2) || (u1 == u2));
}
bool operator<=(usdollar u1, usdollar u2)
{
return ((u1 < u2) || (u1 == u2));
}
usdollar &operator+=(usdollar &u1, usdollar u2)
{
u1 = u1 + u2;
return u1;
}
usdollar &operator-=(usdollar &u1, usdollar u2)
{
u1 = u1 - u2;
return u1;
}
usdollar &operator*=(usdollar &u1, double n)
{
u1 = u1 * n;
return u1;
}
usdollar &operator/=(usdollar &u1, double n)
{
u1 = u1 / n;
return u1;
}

//main()
int main()
{
using namespace std;

// self documenting code begin
cout << "This program calculates the amount of change\ngiven back after a purchase\n\n";
// self documening code end
cout << "Enter the purchase amount: \$";
usdollar purchase;
cin >> purchase;
cout << "Enter the amount of money given: \$";
usdollar money;
cin >> money;
cout << "\n\n";

usdollar change = money - purchase;

//if negative
if(change < 0)
{
cout << "Not enough money! Customer still owes " << change << "!\n";
}
else if(change == 0)
{
cout << "Customer has paid exact amount! No need to return change!\n";
}
//calculate change
else
{
//various denominations
usdollar denominations[] = {
1000.00,
500.00,
100.00,
50.00,
20.00,
10.00,
5.00,
1.00,
0.50,
0.25,
0.10,
0.05,
0.01
};
//temp counting array
int count = {0};
//pluran and singular currencies
string namepl[] = {
"grand",
"five hundred dollars",
"hundred dollars",
"fifty dollars",
"twenty dollars",
"ten dollars",
"five dollars",
"dollars",
"half dollars",
"quarters",
"dimes",
"nickels",
"pennies"
};
string namesg[] = {
"grand",
"five hundred dollars",
"hundred dollars",
"fifty dollars",
"twenty dollars",
"ten dollars",
"five dollars",
"dollar",
"half dollar",
"quarter",
"dime",
"nickel",
"penny"
};
int length = 13;

//for each denomination
for(int i = 0; i < length; ++i)
{
//compute change
for(count[i] = 0; change >= denominations[i]; ++count[i])
{
change -= denominations[i];
}
}

// Self documenting output to screen
cout << "\nPlease give the customer "  << money - purchase << " back in change:\n";
for(int i = 0; i < length; ++i)
{
//if >1 cout plural
if(count[i] > 1)
{
cout << count[i] << " " << namepl[i] << "\n";
}
//if ==1 cout singular
if(count[i] == 1)
{
cout << count[i] << " " << namesg[i] << "\n";
}
//if ==0 then skip
}
}
cout << "\n\n";
system("pause");
return 0;
}```
Hmm I feel a tingling sense of accomplishment...  7. doubles are accurate to DBL_DIG digits
True, but they don't provide PURE precision, because not all decimal fractions can be handled nicely in binary.

I usually store monetary values in an int, multiplying "12.34" by 100 and storing it as "1234".
What if I, a billionaire, wanted to enter \$1234567890.12? The integer would overflow. 8. jafet, thats some awesome code there ;-) I will be using it to get as an example for some other things I need to learn how to do.

I think dwks answered the simple question. Doubles can't work with decimal numbers correctly, so I have made a few mod's to my code and now it's working as it should. I multiplied the purchase and money by 100 and then worked to zero. It no longer fails. Thanks!

Here is an exerpt of code I settled on:

Code:
```                double purchase;
double money;
double change;
int difference;
int dollar = 100;
int halfDollar = 50;
int quarter = 25;
int dime = 10;
int nickel = 5;
int penny = 1;

cout << "This program calculates the amount of change\ngiven back after a purchase";
cout << "\nEnter the purchase amount:  ";
cin >> purchase;
purchase = purchase * 100; // GETS RID OF THE DECIMAL
cout << "\nEnter the amount of money given:  ";
cin >> money;
money = money * 100; //GETS RID OF THE DECIMAL
change = money - purchase;
difference = change; // puts the integer variable into play
change = change / 100; //converts change back to decimal for display
cout << difference <<"  DEBUGGING LOGIC - before we begin\n"; // for debugging``` 9. *shrug* Popular pages Recent additions 