Cod sursa(job #3304244)

Utilizator robigiirimias robert robigi Data 22 iulie 2025 00:25:42
Problema Evaluarea unei expresii Scor 40
Compilator cpp-64 Status done
Runda Arhiva educationala Marime 3.16 kb
#include <fstream>
#include <vector>
#include <stack>
#include <queue>
#include <cassert>
#include <string>

using namespace std;

enum class TokenType { Number, Operator };

struct Token
{
    TokenType type;
    char op;
    int value;

    Token(int v) : type(TokenType::Number), value(v), op(0) {}
    Token(char o) : type(TokenType::Operator), op(o), value(0) {}
};


int main()
{
    ifstream fin("evaluare.in");
    ofstream fout("evaluare.out");

    char c;
    queue<Token> output;
    stack<Token> operators;

    while (fin >> c)
    {
        switch (c)
        {
            case '(':
                operators.push(Token(c));
                break;
            case '*':
            case '/':
                operators.push(Token(c));
                break;
            case '+':
            case '-':
                while (!operators.empty() && (operators.top().op == '*' || operators.top().op == '/'))
                {
                    output.push(operators.top());
                    operators.pop();
                }
                operators.push(c);
                break;
            case ')':
                while (!operators.empty() && operators.top().op != '(')
                {
                    output.push(operators.top());
                    operators.pop();
                }
                assert(!operators.empty());
                assert(operators.top().op == '(');

                if (!operators.empty()) operators.pop(); // Pop the '('
                break;
            default:
                assert(isdigit(c));
                string number;
                number += c;
                while (fin.peek() != EOF && isdigit(fin.peek()))
                {
                    fin >> c;
                    number += c;
                }
                output.push(Token(stoi(number)));
        }
    }

    while (!operators.empty())
    {
        output.push(operators.top());
        operators.pop();
    }

    while (!output.empty())
    {
        operators.push(output.front());
        output.pop();

        if (operators.top().type == TokenType::Number)
        {
            continue; // Skip numbers, they will be processed later
        }

        Token op = operators.top();
        operators.pop();
        Token right = operators.top();
        operators.pop();
        Token left = operators.top();
        operators.pop();

        switch (op.op)
        {
            case '+':
                operators.push(Token(left.value + right.value));
                break;
            case '-':
                operators.push(Token(left.value - right.value));
                break;
            case '*':
                operators.push(Token(left.value * right.value));
                break;
            case '/':
                assert(right.value != 0); // Division by zero check
                operators.push(Token(left.value / right.value));
                break;
            default:
                assert(false); // Invalid operator
        }
    }

    assert(!operators.empty());
    fout << operators.top().value << '\n';
    return 0;
}