Cod sursa(job #3299812)

Utilizator robertcd29Chira Robert-Denis robertcd29 Data 10 iunie 2025 16:53:46
Problema Evaluarea unei expresii Scor 100
Compilator c-64 Status done
Runda Arhiva educationala Marime 3.58 kb
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <ctype.h>

#define MAX_SIZE 200005

char op_stack[MAX_SIZE];
int op_top = -1;

long long val_stack[MAX_SIZE];
int val_top = -1;

char postfix[MAX_SIZE];
int postfix_len = 0;

void push_op(char op) {
    op_stack[++op_top] = op;
}

char pop_op() {
    return op_stack[op_top--];
}

char top_op() {
    if (op_top == -1) return '\0';
    return op_stack[op_top];
}

int is_empty_op() {
    return op_top == -1;
}

void push_val(long long val) {
    val_stack[++val_top] = val;
}

long long pop_val() {
    return val_stack[val_top--];
}

int precedence(char op) {
    if (op == '+' || op == '-') return 1;
    if (op == '*' || op == '/') return 2;
    return 0;
}

int is_operator(char c) {
    return c == '+' || c == '-' || c == '*' || c == '/';
}


void infix_to_postfix(char* infix) {
    int len = strlen(infix);
    
    for (int i = 0; i < len; i++) {
        char c = infix[i];
        
        if (c == ' ') continue; 
        
        if (isdigit(c)) {
            while (i < len && isdigit(infix[i])) {
                postfix[postfix_len++] = infix[i++];
            }
            postfix[postfix_len++] = ' '; 
            i--; 
        }
        else if (c == '(') {
            push_op(c);
        }
        else if (c == ')') {
            while (!is_empty_op() && top_op() != '(') {
                postfix[postfix_len++] = pop_op();
                postfix[postfix_len++] = ' ';
            }
            if (!is_empty_op()) pop_op();
        }
        else if (is_operator(c)) {
            while (!is_empty_op() && top_op() != '(' && 
                   precedence(top_op()) >= precedence(c)) {
                postfix[postfix_len++] = pop_op();
                postfix[postfix_len++] = ' ';
            }
            push_op(c);
        }
    }
    
    while (!is_empty_op()) {
        postfix[postfix_len++] = pop_op();
        postfix[postfix_len++] = ' ';
    }
    
    postfix[postfix_len] = '\0';
}

long long evaluate_postfix() {
    int i = 0;
    
    while (i < postfix_len) {
        if (postfix[i] == ' ') {
            i++;
            continue;
        }
        
        if (isdigit(postfix[i])) {
            long long num = 0;
            while (i < postfix_len && isdigit(postfix[i])) {
                num = num * 10 + (postfix[i] - '0');
                i++;
            }
            push_val(num);
        }
        else if (is_operator(postfix[i])) {
            long long b = pop_val();
            long long a = pop_val();
            long long result;
            
            switch (postfix[i]) {
                case '+': result = a + b; break;
                case '-': result = a - b; break;
                case '*': result = a * b; break;
                case '/': result = a / b; break;
            }
            
            push_val(result);
            i++;
        }
        else {
            i++;
        }
    }
    
    return pop_val();
}

int main() {
    FILE *fin = fopen("evaluare.in", "r");
    if (fin == NULL) {
        fprintf(stderr, "Eroare la deschidere\n");
        return 1;
    }

    FILE *fout = fopen("evaluare.out", "w");
    if (fout == NULL) {
        fprintf(stderr, "Eroare la deschidere\n");
        fclose(fin);
        return 1;
    }
    
    char expression[MAX_SIZE];
    fgets(expression, MAX_SIZE, fin);
    
    int len = strlen(expression);
    if (expression[len-1] == '\n') {
        expression[len-1] = '\0';
    }
    
    infix_to_postfix(expression);
    
    long long result = evaluate_postfix();
    
    fprintf(fout, "%lld\n", result);
    
    fclose(fin);
    fclose(fout);
    
    return 0;
}