zoukankan      html  css  js  c++  java
  • 用栈对后缀表达式求值的算法(五种)

      转载出处:http://blog.csdn.net/yrr6946996/archive/2008/10/22/3127072.aspx


     第一种

    /* 此程序的功能是求出用户输入的整形表达式的值*/
    /*输入的表达式请用#结尾,比如:2+3+5,应输入:2+3+5#。*/
    #include <stdio.h>
    #define   MAXSIZE 16

    typedef struct{
          int data[MAXSIZE];
          int top;
          int base;
        }seqstack;   /* 顺序栈的定义*/
    /*以下为函数声明*/
    void InitStack(seqstack *);       
    int Empty(seqstack *);
    void Push(seqstack *, int );
    int Pop(seqstack *);
    int GetTop(seqstack *);
    int Operate(int ,char ,int );
    char Proceed(char ,char );
    int In(char );
    int EvalExpres(void);
     
    /* 定义两个栈分别存放运算符和操作数*/
    seqstack StackR,StackD;

    /*主函数*/
    int main()
    {
    int v;
    char ch;
    while(1)
    {
        printf("end with #,for example 2+3+5 input:2+3+5#\n");
          printf("calculate:") ;
        v = EvalExpres();        
        printf("The result is:%d",v);
                     /*以下为程序控制*/        
       printf("\nInput 'q' to quit and ENTER run again:");
        do{  
             scanf("%c",&ch);     
          if(ch == 'q' || ch == 'Q')
         exit(0);
         }while(ch!='\n');
    system("cls");
    }
    return 0;
    }

    void InitStack(seqstack *s)
    {     s->top = 0;
          s->base = 0;
    }   /* 初始化栈*/


    int Empty(seqstack *s)
    {   if(s->top == s->base)
                 return 1;
         else
            return 0;
    }    /* 判断栈是否为空*/


    void Push(seqstack *s, int x)
    {   
        if(s->top == MAXSIZE)
             {    printf("OVER FLOW!\n");
                  exit(0);
             }
        else
             {    s->data[s->top] = x;
                  s->top++;
             }    
    }    /* 进栈 */

    int Pop(seqstack *s)
    {    int e;
         if(Empty(s))
            {   printf("Under flow!\n");
                 return 0;
            }   /* 下溢*/
         else
            {   s->top--;
              e = s->data[s->top];
                return e;
            }
    } /* 出栈*/

    int GetTop(seqstack *s)    /*取栈顶元素*/
    {  
        if(Empty(s))
            {   printf("Under flow!\n");
                 return 0;
            }
       else
          return s->data[s->top-1];     
    }

    int EvalExpres(void)    /* 表达式求解函数*/
    {
         int a,b,i=0,s=0;
         char c[80],r;
         InitStack(&StackR);
         Push(&StackR,'#');
         InitStack(&StackD);
         printf(" end with #");
         gets(c);
         while(c[i]!='#' || GetTop(&StackR)!='#')
          {     
             if(!In(c[i]))   /* 判断读入的字符不是运算符 是则进栈*/
               { if(c[i] >= '0' && c[i] <= '9')
                    {
                      s += c[i]-'0';     
                      while(!In(c[++i]))    /*此处实现的功能为当输入的数字为多位数时*/
                      { s*=10;
                        s += c[i]-'0';
                      }
                    Push(&StackD,s+'0');
                      s = 0;
                    }
                 else
                  {
                    printf("wrong!\n");
                      return 0;
                  }           
               }
          else        
             switch(Proceed(GetTop(&StackR),c[i])) /* 此函数用来比较读取的运算符和栈顶运算符的优先级*/
               {
                   case '<':   /* 栈顶的元素优先级高*/
                     Push(&StackR,c[i]);
                        i++;
                      break;
                   case '=':   /* 遇到匹配的小括号时则去掉他*/
                     Pop(&StackR);
                     i++;
                      break;
                   case '>': /* 栈顶的优先级低则出栈并将结果写入栈内*/
                     r = Pop(&StackR);
                     a = Pop(&StackD)-'0';
                     b = Pop(&StackD)-'0';
                     Push(&StackD,Operate(a,r,b)) ;
                      break;               
               }
          }
    return (GetTop(&StackD)-'0');   /* 返回运算结果*/
    }

    int In(char c)         /*问题2:解决In函数问题:判断C是否为运算符是返回1否则返回0*/
    {
       char ch[7]={'+','-','*','/','#','(',')'};
       int i;
       for(i = 0; i < 7; i++)
              if(c == ch[i])
                 return 1;
                
                 return 0;           
    }

    char Proceed(char op,char c) /*op为栈顶元素,c为当前读入的运算符,比较二者的优先级*/
    {                                                    /*问题1:解决Proceed函数*/
          char ch;             
          if(op=='(' && c==')' || op=='#' && c=='#' )
              ch = '=';
    else
          if(op=='+' || op=='-')     /*栈顶元素为‘+’或‘-’的时候*/
            switch(c)
               {
                  case '+':
                  case '-':
                  case ')':
                  case '#': ch = '>'; break;
                  case '*':
                  case '/':
                  case '(': ch = '<';
               }
    else
          if(op=='*' || op=='/')    /*栈顶元素为‘*’或‘/’的时候*/
            switch(c)
               {
                 case '+':
                 case '-':
                 case '*':
                 case '/':    
                 case ')':
                 case '#':    ch = '>'; break;
                 case '(':    ch = '<';
               }
    else
          if(op=='(')             /*栈顶元素为‘(’的时候*/
            switch(c)
               {
                 case '+':
                 case '-':
                 case '*':
                 case '/':
                 case '(': ch = '<'; break;
                 case '#':   printf("Error!\n"); exit(0);
               }
    else
          if(op==')')     /*栈顶元素为‘)’的时候*/
            switch(c)
               {
                 case '+':
                 case '-':
                 case '*':
                 case '/':
                 case '#': ch = '>'; break;
                 case '(': printf("Error!\n"); exit(0);
               }
    else
          if(op=='#')              /*栈顶元素为‘#’的时候*/
            switch(c)
               {
                 case '+':
                 case '-':
                 case '*':
                 case '/':
                 case '(': ch = '<'; break;
                 case ')':   printf("Error!\n"); exit(0);
               }
    return ch;                              
    }          
    /*   问题3:解决Operate函数*/
    int Operate(int a,char r,int b) /*返回由aRb的值 */
    {
       int s;
       int d1 = a;
       int d2 = b; /*把字符ab变为对应数字*/
       switch(r)
          {
             case '+': s = d1+d2; break;
             case '-': s = d2-d1; break;
             case '*': s = d1*d2; break;
             case '/': s = d2/d1;   
          }
    return (s+'0');   
    }


    第二种

    #include <stdio.h>
    #include <malloc.h>

    #define MaxSize 50

    void trans(char *exp,char *postexp)
    {
        struct
        {
            char data[MaxSize];
            int top;
        } op;
        int i=0;
        op.top=-1;
        while(*exp!='\0')
        {
            switch(*exp)
            {
                case '(':
                    op.top++;op.data[op.top]=*exp;
                    exp++;break;
                case ')':
                    while(op.data[op.top]!='(')
                    {
                        postexp[i++]=op.data[op.top];
                        op.top--;
                    }           
                    op.top--;exp++;break;   
                case '+':
                case '-':
                    while(op.top!=-1&&op.data[op.top]!='(')
                    {
                        postexp[i++]=op.data[op.top];
                        op.top--;
                    }       
                    op.top++;op.data[op.top]=*exp;exp++;break;
                case '*':
                case '/':
                    while(op.data[op.top]=='*'||op.data[op.top]=='/')
                    {
                        postexp[i++]=op.data[op.top];
                        op.top--;
                    }
                    op.top++;op.data[op.top]=*exp;exp++;break;
                case ' ':break;
                default:
                    while(*exp>='0'&&*exp<='9')
                    {
                        postexp[i++]=*exp;
                        exp++;
                    }    
                    postexp[i++]='#';
            }   
        }  
        while(op.top!=-1)
        {
            postexp[i++]=op.data[op.top];
            op.top--;
        }  
        postexp[i]='\0';
    }  

    float compvalue(char *postexp)
    {
        struct
        {
            float data[MaxSize];
            int top;
        } st;
        float a,b,c,d;
        st.top=-1;
        while(*postexp!='\0')
        {
            switch(*postexp)
            {
                case '+':
                    a=st.data[st.top];
                    st.top--;
                    b=st.data[st.top];
                    st.top--;
                    c=b+a;
                    st.top++;
                    st.data[st.top]=c;
                    break;
                case '-':
                    a=st.data[st.top];
                    st.top--;
                    b=st.data[st.top];
                    st.top--;
                    c=b-a;
                    st.top++;
                    st.data[st.top]=c;
                    break;
                case '*':
                    a=st.data[st.top];
                    st.top--;
                    b=st.data[st.top];
                    st.top--;
                    c=b*a;
                    st.top++;
                    st.data[st.top]=c;
                    break;
                case '/':
                    a=st.data[st.top];
                    st.top--;
                    b=st.data[st.top];
                    st.top--;
                    if(a!=0)
                    {
                        c=b/a;
                        st.top++;
                        st.data[st.top]=c;
                    }   
                    else
                    {
                        printf("\n\t除零错误!\n");
                        exit(0);
                    }   
                    break;
                default:
                    d=0;
                    while(*postexp>='0'&&*postexp<='9')
                    {
                        d=10*d+*postexp-'0';
                        postexp++;
                    }   
                    st.top++;
                    st.data[st.top]=d;
                    break;
            }   
            postexp++;
        }   
        return st.data[st.top];
    }  

    int main()
    {
        char exp[MaxSize],postexp[MaxSize];
        while(scanf("%s",&exp)!=EOF)
        {
            trans(exp,postexp);
            printf("zhongzhuibiaodashi:  %s\n",exp);
            printf("houzuibiaodashi:     %s\n",postexp);
            printf("zhi:                 %g\n",compvalue(postexp));
        }   
        return 0;
    }  


    第三种

    #include<stdio.h>
    #include<stdlib.h>
    #define add  43
    #define subs 45
    #define mult 42
    #define div 47
    #define MAXSIZE 100

    typedef struct
    {
        int data[MAXSIZE];
        int top;
    }seqstack;
    seqstack *s;

     seqstack *Init()  /*栈的初始化*/
    {
     seqstack *s;
     s=(seqstack *)malloc(sizeof(seqstack));
     if(!s)
        {printf("FULL!");
         return NULL;
         }
      else
        {s->top=-1;
         return s;
         }
     }


     int Empty(seqstack *s)  /*栈空的判断*/
     {if(s->top==-1) return 1;
       else return 0;
      }

     int Push(seqstack *s,int x) /*入栈*/
     {if(s->top==MAXSIZE-1) return 0;
       else
           {s->top++;
            s->data[s->top]=x;
            return 1;
            }
      }

      int Pop(seqstack *s,int *x) /*出栈的算法*/
      {if (Empty(s))  return 0;
       else
          {*x=s->data[s->top];
           s->top--;
           return 1;
           }
       }


       int Top(seqstack *s)       /*取栈顶元素*/
       {if(Empty(s)) return 0;
         else return s->data[s->top];
        }

       int eval(char t,int a1,int a2)
       {switch(t)
             {case add:return(a1+a2);
              case subs:return(a1-a2);
              case mult:return(a1*a2);
              case div:return(a1/a2);
              }
        }

        void main()
        {char c;
         int op1,op2,temp,c1;
         s=Init();
         printf("Input:(end with #)\n");
         while((c=getchar())!='#')
           {if(c=='')continue;
            if(c>47&&c<58)
              {putchar(c);
               c1=c-48;
               Push(s,c1);
               }
            else if(c==add||c==subs||c==mult||c==div)
                 {putchar(c);
                  Pop(s,&op1);
                  Pop(s,&op2);
                  temp=eval(c,op2,op1);
                  Push(s,temp);
                  }
             else printf("It's wrong!\n");
            }
         Pop(s,&op1);
         printf("=%d\n",op1);
         getch();
        }

    第四种

    #include<stdio.h>
    #include<stdlib.h>
    #define add  43
    #define subs 45
    #define mult 42
    #define div 47
    #define MAXSIZE 100

    typedef struct
    {
        int data[MAXSIZE];
        int top;
    }STKzone;
    typedef STKzone *STK;
    typedef enum{ture=1,false=0} bool;
    typedef enum{ok,error} status;
    STKzone expSTKzone;
    STK expSTK;

    STK initSTK(STKzone *stkzone) /*栈的初始化*/
    {STK p;
    p=stkzone;
    p->top=0;
    }

    status push(int *term,STK pstk) /*入栈*//*term前可以没有*,同时将第28、71、81行稍作修改即可 */
    {if(pstk->top==MAXSIZE) return error;
     pstk->data[pstk->top]=*term;
     pstk->top++;
     return ok;
     }

     bool emptySTK(STK pstk)   /*栈空的判断*/
     {return (pstk->top==0);
     }

     status pop(int *pdata,STK pstk)  /*出栈的算法*/
     {if (emptySTK(pstk)) return error;
      (pstk->top)--;
      *pdata=pstk->data[pstk->top];
      return ok;
      }


      void synerror()
      {printf("\nyu fa cuo wu!");


      }

      int eval(char tag,int a1,int a2)
      {switch(tag)
             {case add:return(a1+a2);
              case subs:return(a1-a2);
              case mult:return(a1*a2);
              case div:return(a1/a2);
              }
      }


      main()
      { char c;
         int op1,op2,temp,c1;
         expSTK=initSTK(&expSTKzone);
         printf("Input:\n");
         while((c=getchar())!='\n')
           {if(c=='')continue;
            if(c>47&&c<58)
              {putchar(c);
               c1=c-48;
               if(push(&c1,expSTK)==error)
               {printf("\n too long!\n");

                }
               }
            else if(c==add||c==subs||c==mult||c==div)
                {putchar(c);
                 if(pop(&op1,expSTK)==error)synerror();
                 if(pop(&op2,expSTK)==error)synerror();
                 temp=eval(c,op2,op1);
                 push(&temp,expSTK);
                 }
             else synerror();
            }
         if(pop(&op1,expSTK)==error) synerror();
         if(!(emptySTK(expSTK))) synerror();
         printf("=%d\n",op1);
         getch();
        }

    第五种

    #include<stdio.h>
    #include<stdlib.h>
    #define add  43
    #define subs 45
    #define mult 42
    #define div 47
    #define MAXSIZE 100

    typedef struct
    {
        int stkdata[MAXSIZE];
        int top;
    }stack;

    int init_stack(stack *s)
    { s=(stack *)malloc(sizeof(stack));
     if(!s)
       {printf("FULL!\n");
        return 0;
        }
     else
        {s->top=-1;
         return 1;
         }
    }

    int push(stack *s,int x)
    { if(s->top==MAXSIZE-1)
        { printf("over flow\n");
          return 0;
        }
       else
        {s->top++;
         s->stkdata[s->top]=x;
         return 1;
        }
    }

    char pop(stack *s)

    {   char e;
        if(s->top==-1)
        {
            printf("under flow \n");
            return 0;
        }
        e=s->stkdata[(s->top)--];
        return e;
    }

    void main()
    {
        stack *s1;
        int length,i,num1,num2,result,sum;
        char s[100];
        init_stack(s1);
        printf("please input \n");
        printf("warning:must less than 100\n");
        gets(s);
        length=strlen(s);
        for(i=0;i<=length-1;i++)
         {  if(s[i]>='1'&&s[i]<='9')
             push(s1,s[i]-48);
                else
                {   num1=pop(s1);
                    num2=pop(s1);
                    switch(s[i])
                    {
                      case add: {sum=num1+num2;
                                 push(s1,sum);
                                 break;
                                 }
                      case subs:{sum=num2-num1;
                                 push(s1,sum);
                                 break;
                                 }
                        case div:{sum=num2/num1;
                                  push(s1,sum);
                                  break;
                                 }

                        case mult:{sum=num1*num2;
                                   push(s1,sum);
                                   break;
                                   }
                    }
                }
            }
            result=s1->stkdata[s1->top];
            printf("result is %d\n",result);
            getch();
        }

    在研究表达式。。。无意中看到这。。。太精典了。。。不得不转啊。。。

  • 相关阅读:
    Statement
    打印页数设定
    点选TOP后并不是直接跳到页顶的,而是滚动上去
    文本框不允许输入特殊字符,只能是数字、字母、-和_,不允许输入空格键
    不间断滚动
    无限级别的菜单(侧拉菜单)
    筛法求素数
    1212
    触发器引发的entityframework异常
    using crystalreport generate PDF2
  • 原文地址:https://www.cnblogs.com/ccmfc/p/1721338.html
Copyright © 2011-2022 走看看