Cod sursa(job #561664)

Utilizator sunt_emoSunt emo sunt_emo Data 20 martie 2011 23:52:22
Problema Evaluarea unei expresii Scor 90
Compilator c Status done
Runda Arhiva educationala Marime 3.86 kb
#include <stdio.h>
#include <stdlib.h>
#include <string.h>

typedef struct nod
{
    char *data;
    struct nod * link;
} nod;

void init (nod **st)
{
    (*st)=NULL;
}

void push (nod **st,char *s)
{
    nod *p=(nod*) malloc (sizeof (nod));
    p->data=strdup (s);
    p->link=*st;
    *st=p;
}

void pop (nod **st,char **rez)
{
    if (*st==0) (*rez)[0]=0;
    else
    {
        nod *p=*st;
        *rez=strdup (p->data);
        (*st)=(*st)->link;
        free (p->data);
        free (p);
    }
}

int ord (char *oper)
{
    if (oper[0]=='+'||oper[0]=='-') return 1;
    if (oper[0]=='*'||oper[0]=='/') return 2;
    return 0;
}

int extr (char **s,char *rez)
{
    if ((*s)[0]=='(')
    {
        rez[0]=(*s)[0];
        rez[1]=0;
        (*s)++;
        return 1;
    }
    if ((*s)[0]==')')
    {
        rez[0]=(*s)[0];
        rez[1]=0;
        (*s)++;
        return 2;
    }
    if ((*s)[0]=='+'||(*s)[0]=='-'||(*s)[0]=='*'||(*s)[0]=='/')
    {
        rez[0]=(*s)[0];
        rez[1]=0;
        (*s)++;
        return 3;
    }
    if ((*s)[0]>='0'&&(*s)[0]<='9')
    {
        int k=0;
        while ((*s)[k]>='0'&&(*s)[k]<='9')
        {
            rez[k]=(*s)[k];
            k++;
        }
        rez[k]=0;
        (*s)+=k;
        return 4;
    }
    rez[0]=0;
    return 0;
}

void itooa (int o,char *rez)
{
    int k=0,i=1;
    if (o<0)
    {
        rez[0]='-';
        k++;
        o=-o;
    }
    while (10*i<=o) i*=10;
    while (i>0)
    {
        rez[k]=o/i+'0';
        o%=i;
        i/=10;
        k++;
    }
    rez[k]=0;
}

void calcul (char *rez1,char *rez2,char op,char ** rez)
{
    int op1=atoi (rez1);
    int op2=atoi (rez2);
    int o;
    switch (op)
    {
        case '+':
            o=op1+op2;
            break;
        case '-':
            o=op1-op2;
            break;
        case '/':
            o=op1/op2;
            break;
        case '*':
            o=op1*op2;
            break;
    }
    itooa (o,*rez);
}

int main ()
{
    FILE *in,*out;
    char *s=(char*) malloc (100010);
    char * rez=(char*) malloc (20);
    char * rez2=(char*) malloc (20);
    char * rez3=(char*) malloc (20);
    nod *st1,*st2;
    init (&st1); init (&st2);
    pop (&st1,&rez);
    in=fopen ("evaluare.in","r");
    out=fopen ("evaluare.out","w");
    fgets (s,100010,in);
    int i;
    do
    {
        i=extr (&s,rez);
        switch (i)
        {
            case 1:
                push (&st1,rez);
                break;
            case 2:
                while (1)
                {
                    pop (&st1,&rez);
                    if (rez[0]!='(') push (&st2,rez);
                    else break;
                }
                break;
            case 3:
                while (1)
                {
                    pop (&st1,&rez2);
                    if (ord (rez2)>=ord (rez)) push (&st2,rez2);
                    else {
                        if (rez2[0]!=0) push (&st1,rez2);
                        break;
                    }
                }
                push (&st1,rez);
                break;
            case 4:
                push (&st2,rez);
                break;
        }
    }
    while (i);
    while (st1)
    {
        pop (&st1,&rez);
        push (&st2,rez);
    }
    init (&st1);
    while (st2)
    {
        pop (&st2,&rez);
        push (&st1,rez);
    }
    init (&st2);
    while (st1)
    {
        pop (&st1,&rez);
        if (rez[0]>='0'&&rez[0]<='9') push (&st2,rez);
        else
        {
            pop (&st2,&rez2);
            pop (&st2,&rez3);
            calcul (rez3,rez2,rez[0],&rez);
            push (&st2,rez);
        }
    }
    pop (&st2,&rez);
    fputs (rez,out);
    fprintf (out,"\n");
    fclose (in); fclose (out);
    return 0;
}