//McCabe, Micheal H.
//CSCI-130 Section 002 Introduction to Problem Solving and Programming Using C++
//Professor Schuyler
//January 28, 2009
//
//Assignment #4A (Revised)
//Due January 28, 2009
//
//This program was originally submitted as Assignment #4A on January 22, 2009.
//
//The following changes were implemented at the request of Prof. Schuyler:
//
// 1.) The user can now specify the base for output data (base 2 to base 16)
// 2.) The range of acceptable input values (base 10) is now 0 - 2^31
// 3.) Control logic has been repaired to exit more gracefully
//
//The method in question was derived from examples presented in class.  The
//only reference utilized was the textbook:  Programming and Problem Solving
//with C++, 4th Edition, by Nell Dale & Chip Weems, Copyright 2005 by Jones
//and Bartlett Publishers, Sudbury, MA, USA.  ISBN 13:978-0-7637-0798-9
//
//Actual Program Text Begins Here...
//
//Standard Declarations to get the C++ Preprocessor to actually pass the source
//code to the compiler...

#include <iostream>
using namespace std;

//Now, define the entry point for Main and get on with it...

int main()
{   
    
//Declare the constants and variables for this program

    const string symbols="0123456789ABCDEF";
    long base10_value=0;
    int place=31;            //maximum length for binary integer is 31 bits
    long dividend=0;
    long divisor=10;          //added divisor as a variable to replace "12" as the base.
    long quotient=0;
    long remainder=0;
    string outputstring = "";
    
//Print an introductory message and and tell the user how to escape

    cout << "This program converts a base-10 number in the range 0 to 2^31 to" << endl;
    cout << "the equivalent value in a base specified by the user (2-16)" << endl;
    cout << endl;
    cout << "To end the program, enter a negative value or a nonsense base (b<2 or b>16)";
    cout << endl;
    
//Prompt the user for values and perform a sanity check. If any of the input
//values, the program terminates with an error condition.


     cout << "Please enter a decimal value in the range 0 - 2^31: ";
     cin >> base10_value;
     cout << "Thank you.  Please enter the desired base for output: ";
     cin >> divisor;

     if (base10_value<0) {cout << "Value less than zero!" << endl; return 1;}
     if (base10_value>2147483647) {cout << "Value greater than 2^31." << endl; return 1;}
     if (divisor<2) {cout << "Base too low!" << endl; return 1;}
     if (divisor>16) {cout << "Base too high!" << endl; return 1;}

//Actual processing begins here.

//Move the input value into dividend.  This allows us to save the input data.

    dividend=base10_value;

//For a special case -- if the input value is less than one, we never make it to
//the loop where we create the output string.  The value of zero in any
//valid (for this program) base is zero, so we will set the output string
//to zero in the special case.

if (base10_value<1) 
 { outputstring="0";}
else
 {          

//Here's the main loop. 

    while (dividend>0)
	{     
//We find the modulus of the dividend divided by the base and store this in remainder.
//The remainder here will represent the base-n digit in the place-value system.

     	remainder=dividend%divisor;
              
//We also find the integer quotient, since that now becomes the dividend for the
//next place in the number.

    	quotient=dividend/divisor;
       
//This was also tricky for a BASIC programmer.  Using the remainder as our 
//pointer, we find the correct glyph stored in the constant symbols and 
//concatenate this to the left side of the output string.  As we procede from
//the high-order digits to the low-order digits, the output string is built
//left to right (little endian.)
            
    	outputstring=symbols.substr(remainder,1)+outputstring;
             
//After adding the current digit to the output string, we replace the dividend
//with the quotient from the last cycle and repeat until done.

    	dividend=quotient;

   	}
 }
//When we've completed the whileloop, control passes to this statement and we
//send the output string to standard output. 

     cout << "The answer is: "<< outputstring << endl;

//In this case, the next statement ends my program and returns control to the
//program that called it (presumably, the operating system.) The zero indicates
//that the program concluded normally.
              
    return 0;
    }  

//Finally, the last curly brace in the file indicates the end of routine MAIN,
//and (in this case), the end of my program text.



