Get menu selection again when invalid entry - mortgage calculator

Hi,
My mortgage programisbelow.Ihave everything working fine, except whena user enters an invalid choice from the loan menu, I would like to ask them to re-enter just that value rather than having them do another loan and have them re-enter the amount again. Can someone point me in the right direction?
Thanks

Here is the code

/*
Version 1.0 September 24, 2007 Jon Schab
Original program created. Calculates and displays the mortgage information for
a $200,000.00 loan over a 30 year term at 5.75%. Data is hard coded in the program.

Version 2.0 October 1, 2007 Jon Schab
Modified program to allow user to input of mortgage amount, term, and interest rate.
User also can choose to calculate another loan or exit the program.
Program also altered to be composed of functions rather than being written in main.
Code added to validate numeric entries in loan amount and term. Validation also added
to validate double is entered  for interest rate.
 
Version 3.0 October 8, 2007 Jon Schab
Modified program to consolidate input functions into one Call. The program accepts
the 3 inputs as in the previous version, but in addition to displaying the loan payment
amount, the program now also lists an amortization table for the loan indicating the
payment number, remaining loan balance, principle applied for each payment, and
interest applied for each payment. For longer-term loans, a wait is used to prevent
the data from scrolling off of the screen. Additional validation and messages have been
coded for no user input, as well as 0 input.

@author Jon Schab
@version 3.0


*/


#include <cmath>
#include <iostream>
#include <iomanip>
#include <string>
using namespace std;

// method to cause screen pause
void wait()
      {
            cin.ignore(100,'\n');
            cout << "\nPress Enter to Continue";
            cin.get();
      }

// function to validate loan amount
double read_double()
{

string s;
double d = 0;
char *pCnvEnd;

while (1)
{
getline(cin,s);

d = strtod(s.c_str(), &pCnvEnd);
if (*pCnvEnd != NULL || 0 == s.length()) // check for "nothing" also


{
// invalid chars in string, not an integer
cout << "Not a valid number, please re-enter the value" << " ";
}
else
{
if (d == 0)
cout << "Please enter a non-zero value " << " ";
else break; //valid and non-zero input, stop loop <------------------

}
}

return d;
}

void getInput(double &loanAmount){
     cout << "\t\t\tJon's Mortgage Calculator" << endl << endl;
    // Calculator Title
    cout << "\n\n \t\t\t Loan amount: $"; // ask user for loan amount
    loanAmount = read_double(); // capture loan amount
    }

void printLoanPayments(int payment, double loanBalance, double monthlyPrinciple, double monthlyInterest){
  // print verbage and data values
   cout << " " << setw(15) << payment;
   cout << " " << setw(15) << fixed << setprecision(2) << fabs(loanBalance);
   cout << " " << setw(15) << fixed << setprecision(2) << monthlyPrinciple;
   cout << setw(15) << fixed << setprecision(2) << monthlyInterest << endl;
  }

void computeMortgage(double &loanAmount, int &termYears, double &interestRate){
   int payment = 0; // payment incrementor
   int termMonths; // term in months
   double monthlyPayment; // monthly payment

   double monthlyInterest; // vaiable to hold monthly interest paid
   double loanBalance; // variable to hold descending loan balance
   int months = 0; // month incrementor
   double monthlyPrinciple; // variable to hold monthly principle paid
   int lineCount = 1; // variable to count lines for screen pause
   double interestRateMonthly; //
   //calculate term in years and monthly interest rate
   interestRateMonthly = ((interestRate / 12) / 100);
   termMonths = (termYears *12);

   //calculate mothly payment
   monthlyPayment = (loanAmount *interestRateMonthly) / (1-pow(1.0 / (1.0 +
   interestRateMonthly), termMonths));

   //display monthly payment to the screen.
   cout << "\n\n \t\t\t Monthly Payment $" << monthlyPayment << endl << endl;

  loanBalance = loanAmount; // set initial loan balance to loan amount

  // create headings and separator line
  cout << "\t Payment Number" << "\t Loan Balance" << "\t Principle Paid" << "\t Interest Paid" << endl;
  cout << "\t -------------------------------------------------------------" << endl;

  while (loanBalance >= 0.01) //Loop ends when loan is below one penny

  {
    monthlyInterest = (loanBalance *interestRateMonthly);
    // calculate monthly interest
    monthlyPrinciple = monthlyPayment - monthlyInterest;
    // calculate monthly principle
    loanBalance = loanBalance - monthlyPrinciple; // calculate loan balance
    loanAmount = loanBalance; // assign new balance ot loan amount
    payment++; // increment payment number

   // print verbage and data values
   printLoanPayments(payment, loanBalance, monthlyPrinciple, monthlyInterest);

   loanBalance = loanAmount; // assign remaining balance to loan balance
   lineCount++; // increment line counter

   // count for payment printed to screen
   if (lineCount > 20)
     {
         //pause displays a message and waits for the user to hit a key
         wait();
         lineCount = 0; // Reset line counter

        // reprint headings
        cout << "\t Payment Number" << "\t Loan Balance" << "\t Principle Paid" << "\t Interest Paid" << endl;
        cout << "\t -------------------------------------------------------------" << endl;

       }
    }
  }

string menu(){
   string choice = "";
   cout<<"\n\t\t************ Mortgage Options *************";
   cout<<"\n\t\t*  1. 7 years at 5.35%";
   cout<<"\n\t\t*  2. 15 years at 5.5%";
   cout<<"\n\t\t*  3. 30 years at 5.75%";
   cout<<"\n\t\t*************************  Enter Choice:   ";
   cin >> choice;
   return choice;      
 }
 
int main()
{
 string choice = "";
 double loanAmount ; //laon amount
 double interestRate [3] = {5.35, 5.5, 5.75};
 int termYears [3] = {7, 15, 30};
           
 bool conn = false;
 while(!conn){
   getInput(loanAmount);
   choice = menu();
   
   //decide what option of mortage to compute
   if(choice == "1"){
      computeMortgage(loanAmount,termYears[0],interestRate[0]);        
    }            
   else if(choice == "2"){
      computeMortgage(loanAmount,termYears[1],interestRate[1]);        
    }
   else if (choice == "3"){
      computeMortgage(loanAmount,termYears[2],interestRate[2]);        
    }            
   else
      cout<<"\n\tInvlid Choice: Please Enter (1-3)\n\n";
   string input = ""; // to continue further
   bool con = false;
   while(!con){
   cout<<"\n\tDo you want to Compute Another Mortgage Loan (y/n): ";
   cin >> input;
   cin.get();

   if(input == "y" || input == "Y")
      {
        input = ""; // to continue again
        con = true;
            system("cls"); // clear the screen
        }
   else if(input == "n" || input == "N")
      {
         cout<<"\n\n\t\t***********  Goodbye ************\n\n";
         con = true;
         conn = true;  
            }
   else
     {
       cout<<"\n\t\tInvlid Choice: Choose(y/n)\n\n";      
      }
     }
 }  

wait();
return 0;
}
ghost8067Asked:
Who is Participating?
 
Infinity08Connect With a Mentor Commented:
This is the location in the code you'll need to modify :

   choice = menu();
   
   //decide what option of mortage to compute
   if(choice == "1"){
      computeMortgage(loanAmount,termYears[0],interestRate[0]);        
    }            
   else if(choice == "2"){
      computeMortgage(loanAmount,termYears[1],interestRate[1]);        
    }
   else if (choice == "3"){
      computeMortgage(loanAmount,termYears[2],interestRate[2]);        
    }     else
      cout<<"\n\tInvlid Choice: Please Enter (1-3)\n\n";

In other words : instead of just printing a message in the else case, you'll have to add another loop around all of this that will get a new choice from the menu as long as an invalid choice was made.

Note that this will be similar to the other two validation loops you already have (the ones based on con and conn).
0
 
UrosVidojevicCommented:
You need to put reading choice value in some loop so that program promts user every time he enters invalid value.

Probably you will have to use do {} while loop. in menu() function

string menu(){
   string choice = "";
   do { // added coode
      cout<<"\n\t\t************ Mortgage Options *************";
      cout<<"\n\t\t*  1. 7 years at 5.35%";
      cout<<"\n\t\t*  2. 15 years at 5.5%";
      cout<<"\n\t\t*  3. 30 years at 5.75%";
      cout<<"\n\t\t*************************  Enter Choice:   ";
      cin >> choice;
   } while (choice[0] < '1' || choice[0] > '3' || choice.length() > 1); // added code
   return choice;      
 }
0
 
ghost8067Author Commented:
Thanks, the loop works fine. One more question. How can I add an error message before displaying the choices again?

Newest code

/*
Version 1.0 September 24, 2007 Jon Schab
Original program created. Calculates and displays the mortgage information for
a $200,000.00 loan over a 30 year term at 5.75%. Data is hard coded in the program.

Version 2.0 October 1, 2007 Jon Schab
Modified program to allow user to input of mortgage amount, term, and interest rate.
User also can choose to calculate another loan or exit the program.
Program also altered to be composed of functions rather than being written in main.
Code added to validate numeric entries in loan amount and term. Validation also added
to validate double is entered  for interest rate.
 
Version 3.0 October 8, 2007 Jon Schab
Modified program to consolidate input functions into one Call. The program accepts
the 3 inputs as in the previous version, but in addition to displaying the loan payment
amount, the program now also lists an amortization table for the loan indicating the
payment number, remaining loan balance, principle applied for each payment, and
interest applied for each payment. For longer-term loans, a wait is used to prevent
the data from scrolling off of the screen. Additional validation and messages have been
coded for no user input, as well as 0 input.

@author Jon Schab
@version 3.0


*/


#include <cmath>
#include <iostream>
#include <iomanip>
#include <string>
using namespace std;

// method to cause screen pause
void wait()
      {
            cin.ignore(100,'\n');
            cout << "\nPress Enter to Continue";
            cin.get();
      }

// function to validate loan amount
double read_double()
{

string s;
double d = 0;
char *pCnvEnd;

while (1)
{
getline(cin,s);

d = strtod(s.c_str(), &pCnvEnd);
if (*pCnvEnd != NULL || 0 == s.length()) // check for "nothing" also


{
// invalid chars in string, not an integer
cout << "Not a valid number, please re-enter the value" << " ";
}
else
{
if (d == 0)
cout << "Please enter a non-zero value " << " ";
else break; //valid and non-zero input, stop loop <------------------

}
}

return d;
}

void getInput(double &loanAmount){
     cout << "\t\t\tJon's Mortgage Calculator" << endl << endl;
    // Calculator Title
    cout << "\n\n \t\t\t Loan amount: $"; // ask user for loan amount
    loanAmount = read_double(); // capture loan amount
    }

void printLoanPayments(int payment, double loanBalance, double monthlyPrinciple, double monthlyInterest){
  // print verbage and data values
   cout << " " << setw(15) << payment;
   cout << " " << setw(15) << fixed << setprecision(2) << fabs(loanBalance);
   cout << " " << setw(15) << fixed << setprecision(2) << monthlyPrinciple;
   cout << setw(15) << fixed << setprecision(2) << monthlyInterest << endl;
  }

void computeMortgage(double &loanAmount, int &termYears, double &interestRate){
   int payment = 0; // payment incrementor
   int termMonths; // term in months
   double monthlyPayment; // monthly payment

   double monthlyInterest; // vaiable to hold monthly interest paid
   double loanBalance; // variable to hold descending loan balance
   int months = 0; // month incrementor
   double monthlyPrinciple; // variable to hold monthly principle paid
   int lineCount = 1; // variable to count lines for screen pause
   double interestRateMonthly; //
   //calculate term in years and monthly interest rate
   interestRateMonthly = ((interestRate / 12) / 100);
   termMonths = (termYears *12);

   //calculate mothly payment
   monthlyPayment = (loanAmount *interestRateMonthly) / (1-pow(1.0 / (1.0 +
   interestRateMonthly), termMonths));

   //display monthly payment to the screen.
   cout << "\n\n \t\t\t Monthly Payment $" << monthlyPayment << endl << endl;

  loanBalance = loanAmount; // set initial loan balance to loan amount

  // create headings and separator line
  cout << "\t Payment Number" << "\t Loan Balance" << "\t Principle Paid" << "\t Interest Paid" << endl;
  cout << "\t -------------------------------------------------------------" << endl;

  while (loanBalance >= 0.01) //Loop ends when loan is below one penny

  {
    monthlyInterest = (loanBalance *interestRateMonthly);
    // calculate monthly interest
    monthlyPrinciple = monthlyPayment - monthlyInterest;
    // calculate monthly principle
    loanBalance = loanBalance - monthlyPrinciple; // calculate loan balance
    loanAmount = loanBalance; // assign new balance ot loan amount
    payment++; // increment payment number

   // print verbage and data values
   printLoanPayments(payment, loanBalance, monthlyPrinciple, monthlyInterest);

   loanBalance = loanAmount; // assign remaining balance to loan balance
   lineCount++; // increment line counter

   // count for payment printed to screen
   if (lineCount > 20)
     {
         //pause displays a message and waits for the user to hit a key
         wait();
         lineCount = 0; // Reset line counter

        // reprint headings
        cout << "\t Payment Number" << "\t Loan Balance" << "\t Principle Paid" << "\t Interest Paid" << endl;
        cout << "\t -------------------------------------------------------------" << endl;

       }
    }
  }

string menu(){
   string choice = "";
   do {
   cout<<"\n\t\t************ Mortgage Options *************";
   cout<<"\n\t\t*  1. 7 years at 5.35%";
   cout<<"\n\t\t*  2. 15 years at 5.5%";
   cout<<"\n\t\t*  3. 30 years at 5.75%";
   cout<<"\n\t\t*************************  Enter Choice:   ";
   cin >> choice;
   } while (choice[0] < '1' || choice[0] > '3' || choice.length() > 1);
   return choice;      
 }
 
int main()
{
 string choice = "";
 double loanAmount ; //laon amount
 double interestRate [3] = {5.35, 5.5, 5.75};
 int termYears [3] = {7, 15, 30};
           
 bool conn = false;
 while(!conn){
   getInput(loanAmount);
   choice = menu();
   
   //decide what option of mortage to compute
   if(choice == "1"){
      computeMortgage(loanAmount,termYears[0],interestRate[0]);        
    }            
   else if(choice == "2"){
      computeMortgage(loanAmount,termYears[1],interestRate[1]);        
    }
   else if (choice == "3"){
      computeMortgage(loanAmount,termYears[2],interestRate[2]);        
    }            
   else
      cout<<"\n\tInvlid Choice: Please Enter (1-3)\n\n";
   string input = ""; // to continue further
   bool con = false;
   while(!con){
   cout<<"\n\tDo you want to Compute Another Mortgage Loan (y/n): ";
   cin >> input;
   cin.get();

   if(input == "y" || input == "Y")
      {
        input = ""; // to continue again
        con = true;
            system("cls"); // clear the screen
        }
   else if(input == "n" || input == "N")
      {
         cout<<"\n\n\t\t***********  Goodbye ************\n\n";
         con = true;
         conn = true;  
            }
   else
     {
       cout<<"\n\t\tInvalid Choice: Choose(y/n)\n\n";      
      }
     }
 }  

wait();
return 0;
}
0
 
UrosVidojevicConnect With a Mentor Commented:
Just add:

   if (choice != "") // Print some error message
      cout << "\nInvalid option. Please try again...\n";

at the beginning of do while loop:

do {
   if (choice != "") // Print some error message
      cout << "\nInvalid option. Please try again...\n";
 // other code...
} while (...);

If choice is not equal to "" then that is not first iteration, so error message should be displayed.
0
 
ghost8067Author Commented:
Thanks for the helpfromboth of you. I should be all set.
0
All Courses

From novice to tech pro — start learning today.