#include <cctype> #include <cstdlib> #include <cstring> #include <iostream> #include <fstream> #include <stack> #include <string> using namespace std; void open_files(ifstream&, ifstream&); double read_and_evaluate(istream& ins); void evaluate_stack_tops(stack<double>& numbers, stack<char>& operations); int main( ) { double answer; string s; ifstream in, exp; open_files(in, exp); while (in) { answer = read_and_evaluate(in); getline(exp, s); cout << s << " = " << answer << endl; } in.close(); exp.close(); return EXIT_SUCCESS; } void open_files(ifstream& i, ifstream& e) { i.open("expressions.dat"); e.open("expressions.dat"); if (i.fail()) { cout << "Attempt to open expressions.dat on \"in\" failed." << endl; exit(1); } if (e.fail()) { cout << "Attempt to open expressions.dat on \"exp\" failed."; exit(1); } } double read_and_evaluate(istream& ins) { const char DECIMAL = '.'; const char RIGHT_PARENTHESIS = ')'; stack<double> numbers; stack<char> operations; double number; char symbol; while (ins && ins.peek( ) != '\n') { if (isdigit(ins.peek( )) || (ins.peek( ) == DECIMAL)) { ins >> number; numbers.push(number); } else if (strchr("+-*/", ins.peek( )) != NULL) { ins >> symbol; operations.push(symbol); } else if (ins.peek( ) == RIGHT_PARENTHESIS) { ins.ignore( ); evaluate_stack_tops(numbers, operations); } else { ins.ignore(); } } ins.ignore(); return numbers.top( ); } void evaluate_stack_tops(stack<double>& numbers, stack<char>& operations) { double operand1, operand2; operand2 = numbers.top( ); numbers.pop( ); operand1 = numbers.top( ); numbers.pop( ); switch (operations.top( )) { case '+': numbers.push(operand1 + operand2); break; case '-': numbers.push(operand1 - operand2); break; case '*': numbers.push(operand1 * operand2); break; case '/': numbers.push(operand1 / operand2); break; } operations.pop( ); }