Midterm Project: Big Positive Real Number Calculator
Midterm-1: Big Positive Real Number in Decimal Point Format (40%)
-
Inputs:
- Input a big positive real number in decimal point format, one line for one number.
- digits before and after the decimal point are at most 9 digits, separated by a point character
.
.
- digits before and after the decimal point are at most 9 digits, separated by a point character
- Input a operator, one line for one operator:
+
: add*
: multiply
- The input is interleaved, one line for one number and one line for one operator after the number.
- Input Ctrl+D to finish the input.
- Windows: Ctrl+Z (will show
^Z
on the screen) then Enter (⏎
in Format) to finish the input.
- Windows: Ctrl+Z (will show
- Input a big positive real number in decimal point format, one line for one number.
-
Outputs:
- The calculation result
- The result is shown in decimal point format, with at most 18 digits before the decimal point, and 9 digits after the decimal point (rounding toward zero, truncate).
- The format please refer to the Format section.
- The calculation result
-
File name:
midterm-1_<student_id>.cpp
(e.g.midterm-1_106062802.cpp
) -
The program will not have any user prompts, only print the result.
-
The program does not need to handle invalid inputs.
-
The program should be finished within 10 seconds. Any test cases will garuntee the program is finished within 10 seconds.
Format
<before dec 1>.<after dec 1>⏎
<op 1>⏎
<before dec 2>.<after dec 2>⏎
<op 2>⏎
...
<before dec n-1>.<after dec n-1>⏎
<op n-1>⏎
<before dec n>.<after dec n>⏎
^Z⏎
<before dec result>.<after dec result>
Example
$ ./a.out
1.0⏎
^Z⏎
1.000000000
$ ./a.out
0.2⏎
^Z⏎
0.200000000
$ ./a.out
1.0⏎
+⏎
2.0⏎
+
3.0⏎
*⏎
4.3⏎
^Z⏎
25.800000000
$ ./a.out
1.000000001⏎
+⏎
2.000000002⏎
^Z⏎
3.000000003
$ ./a.out
123456789.123456789⏎
+⏎
987654321.987654321⏎
^Z⏎
1111111111.111111110
$ ./a.out
1.000000001⏎
*⏎
2.000000002⏎
^Z⏎
2.000000004
$ ./a.out
123456789.123456789⏎
*⏎
987654321.987654321⏎
^Z⏎
121932631356500531.347203169
Reference
Pseudo Code
#include <iostream>
#include <string>
#include <sstream>
#include <iomanip>
using namespace std;
class BigReal
{
private:
// data members
// save the digits before and after the decimal point of a before_decimal number
// with `long long` precision
const long long m_dec_upperbound = 1000000000;
long long m_before_decimal;
long long m_after_decimal; // times 10^-9
void _output_normalization();
public:
// Constructor, initializes before_decimal and after_decimalinary parts
// hint: as like as `modify` function in examples
// but use default constructor to implement
BigReal(const long long &arg_before_decimal = 0.0,
const long long &arg_after_decimal = 0.0);
// Copy constructor
BigReal(const BigReal &arg_big_real);
// assignment operator
BigReal &operator=(const BigReal &arg_big_real);
// add assignment operator
BigReal &operator+=(const BigReal &arg_big_real);
// multiply assignment operator
BigReal &operator*=(const BigReal &arg_big_real);
// add function
BigReal operator+(const BigReal &arg_big_real) const;
// multiply function
BigReal operator*(const BigReal &arg_big_real) const;
// cout `<<` operator for print BigReal number
// note: be careful about the format of output
friend ostream &operator<<(ostream &arg_os, const BigReal &arg_big_real);
// cin `>>` operator for input BigReal number
// note: be careful about the format of input
// hint: use string `+=` to append digits
friend istream &operator>>(istream &arg_is, BigReal &arg_big_real);
};
int main()
{
string input;
BigReal result_complex;
char op = '=';
while (getline(cin, input))
{
// input is a operation
if (input == "+" || input == "*")
{
op = input[0];
continue;
}
else if (input.empty())
{
continue;
}
// input is a BigReal number
else
{
stringstream ss(input);
BigReal current_complex;
ss >> current_complex;
switch (op)
{
case '+':
result_complex += current_complex;
break;
case '*':
result_complex *= current_complex;
break;
case '=':
result_complex = current_complex;
break;
default:
cerr << "Error: unknown operation" << endl;
return 1;
}
}
}
cout << endl;
cout << result_complex << endl;
return 0;
}
TA Version Code
#include <iostream>
#include <string>
#include <sstream>
#include <iomanip>
using namespace std;
class BigReal
{
private:
// data members
// save the digits before and after the decimal point of a before_decimal number
// with `long long` precision
const long long m_dec_upperbound = 1000000000;
long long m_before_decimal;
long long m_after_decimal; // times 10^-9
void _output_normalization()
{
if (m_after_decimal < 0)
{
m_before_decimal -= 1;
m_after_decimal += m_dec_upperbound;
}
if (m_after_decimal > m_dec_upperbound)
{
m_before_decimal += m_after_decimal / m_dec_upperbound;
m_after_decimal = m_after_decimal % m_dec_upperbound;
}
}
public:
// Constructor, initializes before_decimal and after_decimalinary parts
// hint: as like as `modify` function in examples
// but use default constructor to implement
BigReal(const long long &arg_before_decimal = 0.0,
const long long &arg_after_decimal = 0.0)
: m_before_decimal(arg_before_decimal), m_after_decimal(arg_after_decimal)
{
}
// Copy constructor
BigReal(const BigReal &arg_big_real)
: m_before_decimal(arg_big_real.m_before_decimal),
m_after_decimal(arg_big_real.m_after_decimal)
{
}
// assignment operator
BigReal &operator=(const BigReal &arg_big_real)
{
if (this == &arg_big_real) // self-assignment
return *this;
m_before_decimal = arg_big_real.m_before_decimal;
m_after_decimal = arg_big_real.m_after_decimal;
return *this;
}
// add assignment operator
BigReal &operator+=(const BigReal &arg_big_real)
{
m_before_decimal += arg_big_real.m_before_decimal;
m_after_decimal += arg_big_real.m_after_decimal;
_output_normalization();
return *this;
}
// multiply assignment operator
BigReal &operator*=(const BigReal &arg_big_real)
{
long long before_decimal = m_before_decimal * arg_big_real.m_before_decimal;
long long after_decimal = m_after_decimal * arg_big_real.m_after_decimal / m_dec_upperbound;
after_decimal += m_before_decimal * arg_big_real.m_after_decimal;
after_decimal += m_after_decimal * arg_big_real.m_before_decimal;
m_before_decimal = before_decimal;
m_after_decimal = after_decimal;
_output_normalization();
return *this;
}
// add function
BigReal operator+(const BigReal &arg_big_real) const
{
BigReal c(*this);
c += arg_big_real;
return c;
}
// multiply function
BigReal operator*(const BigReal &arg_big_real) const
{
BigReal c(*this);
c *= arg_big_real;
return c;
}
// cout `<<` operator for print BigReal number
// note: be careful about the format of output
friend ostream &operator<<(ostream &arg_os, const BigReal &arg_big_real)
{
arg_os << arg_big_real.m_before_decimal << '.'
<< setfill('0') << setw(9) << arg_big_real.m_after_decimal;
return arg_os;
}
// cin `>>` operator for input BigReal number
// note: be careful about the format of input
// hint: use string `+=` to append digits
friend istream &operator>>(istream &arg_is, BigReal &arg_big_real)
{
string str_before_decimal, str_after_decimal;
getline(arg_is, str_before_decimal, '.');
getline(arg_is, str_after_decimal);
str_after_decimal = str_after_decimal.substr(0, 9);
for (int i = 0; i < 9; i++)
if (i >= str_after_decimal.size())
str_after_decimal += '0';
arg_big_real.m_before_decimal = stoll(str_before_decimal);
arg_big_real.m_after_decimal = stoll(str_after_decimal);
return arg_is;
}
};
int main()
{
string input;
BigReal result_complex;
char op = '=';
while (getline(cin, input))
{
// input is a operation
if (input == "+" || input == "*")
{
op = input[0];
continue;
}
else if (input.empty())
{
continue;
}
// input is a BigReal number
else
{
stringstream ss(input);
BigReal current_complex;
ss >> current_complex;
switch (op)
{
case '+':
result_complex += current_complex;
break;
case '*':
result_complex *= current_complex;
break;
case '=':
result_complex = current_complex;
break;
default:
cerr << "Error: unknown operation" << endl;
return 1;
}
}
}
cout << endl;
cout << result_complex << endl;
return 0;
}