/********************************************************************* C201 Computer Programming II Fall 2006 Dana Vrajitoru & A class to represent large integer numbers. **********************************************************************/ #include #include "number.h" // Some private class methods: // Adds the digits in the two numbers regardless of the sign. void Number::Add_digits(const Number &data) { int sum, report = 0; for (int i=0; i 0 && size < MAX_SIZE) { digits[size] = report; size++; } } // Subtract the digits in the two numbers regardless of the sign. // We'll assume that the digits in the target object represent a // larger unsigned number than the unsigned object data. // Declare a report equal to 0 and i = 0. Use a for loop over the size // of the target object. At every iteration, subtract from digits[i] // both data.digits[i] and the report. If digits[i] becomes negative, // then make the report equal to 1 and add 10 to digits[i]. Otherwise // make the report 0. At the end of the loop, verify if some digits at // the back of the number have become 0 and adjust the counter in that // case (there may be more than one). You'll need another loop for // that, starting from size and going backwards while the digits[i] is // 0. If the size becomes 0 make sure you make the sign plus. void Number::Subtract_digits(const Number &data) { // To be implemented by the student. } // Compare the digits in the two number regardless of the sign. The // function returns -1 if the target object is less than the number // data, 0 if they are identical, and +1 if the target object is // larger than the data. // This should be very similar to a function comparing two strings // (see the text of the homework for its implementation). If the size // of the target object is strictly greater than the size of data, // return 1. If the size of the target object is strictly smaller than // the size of the data, then return -1. If they are equal, then you // need a loop to compare them. Start from the end of the array going // backwards until either you reach 0 and found all the digits equal, // in which case you must return 0, or you find two digits that are // different, let's say at position i. Then if digits[i] is greater // than data.digits[i] return 1, otherwise -1. int Number::Compare_digits(const Number &data) const { // To be implemented by the student. } // Multiplication by a single digit. We need this for the operator *. // You need to declare a report initialized to 0. The you need a loop // over the size in which you multiply digits[i] with d and then add // the report to it, then make the digits[i] become the units of the // result, and the report become the result divided by 10. At the end // if the report is not 0 and the size is not already the max, you // need to store the last report in digits[size], then increase the // size. You must treat the case where d is 0 specially, calling the // function Reset for it. You can also test if d is 1 and leave the // number unchanged in that case. void Number::Multiply(const short int d) { // To be implemented by the student. } // Shifts the digits to the left. This is equivalent to a // multiplication by 10. It moves digits[0] to digits[1], digits[1] to // digits[2], and so on. It must start from the end of the number // (position size -1) and go backwards. It must add a 0 digit at // position 0 and increase the size. If the number is equal to 0, the // function should not change it. void Number::Shift_left() { // To be implemented by the student. } // Constructors // Default constructor: intializes all digits to 0. Number::Number() { Reset(); } // Copy constructor. Number::Number(const Number &data) :size(data.size), sign(data.sign) { for (int i=0; i< MAX_SIZE; i++) digits[i] = data.digits[i]; } // Converting a simple number to an object of the class. Number::Number(const int n) { // We'll use the assignment operator here *this = n; } // Converting a string to an object of the class. Number::Number(const char *s) { // Same as before. *this = s; } // We may need to reset all the digits to 0. void Number::Reset() { for (int i=0; i 0) { digits[i] = m % 10; // last digit in m i++; m = m/10; } size = i; return *this; } Number &Number::operator=(const char *s) { Reset(); size = strlen(s); for (int i=0; i 0) temp.Subtract_digits(data); else { temp = data; temp.Subtract_digits(*this); } } return temp; } // Subtraction. If a and b are numbers, this implements the operation // a - b. // Use the operator+ and the unary operator- to implement this one. // Use the fact that a - b is equal to a + (-b). const Number Number::operator-(const Number &data) const { // To be implemented by the student. } // Sign change const Number Number::operator-() const { Number temp = *this; if (sign == plus_id) temp.sign = minus_id; else temp.sign = plus_id; return temp; } // ***************** Multiplication operator ************************ // We loop over the digits in the second number. For each of them we // multiply the first number (*this) by that digit and by 10 to the // power i, where i is the index. The multiplication by 10 is done by // shifting the digits to the left and adding a 0 at position 0. const Number Number::operator*(const Number &data) const { Number temp1 = *this, temp2, result; for (int i=0; i size) size++; } // If the number is negative, make it positive, decrement it, then // make it negative again, unless by decreasing it, it became 0. else { sign = plus_id; --(*this); if (size != 0) sign = minus_id; } return *this; } // Decrementing operator. It is used as in --n. Number &Number::operator--() { // If the number is 0 then by removing 1 we make it -1. if (size == 0 && digits[0] == 0) { size = 1; digits[0] = 1; sign = minus_id; } else if (sign == plus_id) { int i=0; // Look for the first digit that is not 0: // 200 - 1 = 199. // All the 0s become 9 while (digits[i] == 0) { digits[i] = 9; i++; } // We remove 1 from the first non-zero digit we encounter. digits[i] = digits[i] - 1; // Must check if that was the last digit and if it became 0. In // that case we must decrease the size. if (digits[i] == 0 && i == size-1) size--; } // If the number is negative, we make it positive, we increment it, // then make it negative again. --(-8) becomes -9. else { sign = plus_id; ++(*this); sign = minus_id; } return *this; } // Comparison operators bool Number::operator<(const Number &data) const { if (sign == plus_id) // + ? if (data.sign == plus_id) // + + if (Compare_digits(data) == -1) return true; else return false; else // + - return false; else if (data.sign == plus_id) // - + return true; else if (Compare_digits(data) == 1) // - - return true; else return false; } // Using the fact that a <= b if a b if b < a. bool Number::operator>(const Number &data) const { return (data < *this); } // Can be implemented in a similar way to the operator <=. bool Number::operator>=(const Number &data) const { // To be implemented by the student. } // Use the fact that two objects are equal if they have the same // absolute value, meaning if the function Compare_digits returns 0 // when calles from the target object with the object data as a // parameter, and if they have the same sign. bool Number::operator==(const Number &data) const { // To be implemented by the student. } // Two objects are not equal if the == operator returns false. bool Number::operator!=(const Number &data) const { return !(*this == data); } // Input - output operators. // Write the digits out in reverse order, starting from the last one // at position size -1 going backwards toward 0. See the conversion // from a string to a Number for an example of such a loop. If the // size of the object is 0, output a 0 without anything else. ostream &operator<<(ostream &out, const Number &data) { // To be implemented by the student. } istream &operator>>(istream &in, Number &data) { char str[MAX_SIZE]; in >> str; if (str[0] == '-') { data = str+1; data.sign = minus_id; } else data = str; return in; }