⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 数学061 漆文浩.c

📁 简单的算术表达式求值
💻 C
字号:
#include "stdio.h" 
#include "stdlib.h" 
#include "string.h" 
#define ERROR -1 
#define STACKSIZE 20 
//定义字符类型栈 
   typedef struct{ 
    char stackname[20]; 
    char *base; 
    char *top; 
   } Stack; 
   
   Stack OPTR, OPND; //定义OPTR为运算符栈,OPND为操作数栈  
   char expr[255] = ""; //存放表达式串 
   char *ptr = expr; 
   int step = 0; //计算的步次 
   int InitStack(Stack *s, char *name) { 
       s->base=(char *)malloc(STACKSIZE*sizeof(char)); 
       if(!s->base) exit (ERROR); 
       strcpy(s->stackname, name); 
       s->top=s->base; 
	   return 1; 
       } 
   int In(char ch) { 
       return(ch=='+'||ch=='-'||ch=='*'||ch=='/'||ch=='('||ch==')'||ch=='#'); 
       } 
   void OutputStatus() { 
        char *s; // step  
        printf("\n%-8d", ++step); //OPTR 
        for(s = OPTR.base; s < OPTR.top; s++) 
        printf("%c", *s); printf("\t"); //OPND 
        for(s = OPND.base; s < OPND.top; s++) 
        printf("%d ", *s); printf("\t\t%c", *ptr); 
        } 
   int Push(Stack *s,char ch) { 
       char *name = s->stackname; 
	   OutputStatus(); 
       if(strcmp(name, "OPND") == 0) 
       printf("\tPUSH(%s, %d)", name, ch); 
       else printf("\tPUSH(%s, %c)", name, ch); 
        *s->top=ch; s->top++; 
		return 1; 
        } 
   char Pop(Stack *s) { 
        char p; 
        OutputStatus(); 
        printf("\tPOP(%s)", s->stackname);
         s->top--; 
         p=*s->top; 
         return p; 
         } 
   char GetTop(Stack s) { 
        char p=*(s.top-1); 
        return (p); 
        } 
   //判断运算符优先权,返回优行权高的 
   char Precede(char c1,char c2) { 
        int i=0,j=0; 
        static char array[49]={ '>', '>', '<', '<', '<', '>', '>', 
			                    '>', '>', '<', '<', '<', '>', '>', 
								'>', '>', '>', '>', '<', '>', '>', 
								'>', '>', '>', '>', '<', '>', '>', 
								'<', '<', '<', '<', '<', '=', '!',
								'>', '>', '>', '>', '!', '>', '>', 
								'<', '<', '<', '<', '<', '!', '='
		}; 
        switch(c1) { // i为运算关系优先表的横标 
        case '+' : i=0;break; 
        case '-' : i=1;break; 
        case '*' : i=2;break; 
        case '/' : i=3;break; 
        case '(' : i=4;break; 
        case ')' : i=5;break; 
        case '#' : i=6;break; 
        } switch(c2) { // j为运算关系优先表的纵标
        case '+' : j=0;break; 
        case '-' : j=1;break; 
        case '*' : j=2;break; 
        case '/' : j=3;break; 
        case '(' : j=4;break; 
        case ')' : j=5;break; 
        case '#' : j=6;break; 
        } 
		  return (array[7*i+j]); // 返回运算符  
        } 
     //操作函数  
   int Operate(int a,char op,int b) { 
               OutputStatus(); 
               printf("\tOPERATE(%d, %c, %d)", a, op, b); 
               switch(op) { 
                          case '+' : return (a+b); 
                          case '-' : return (a-b); 
                          case '*' : return (a*b); 
                          case '/' : if (b!=0) return (a/b);
							  else{
								  printf("0不合法.");return 0;}
								  break;
							  
                       }
			   return 0; 
   } 
   int EvalExpr() { 
       char c,theta,x,m; 
       int a,b; 
	   c = *ptr++; 
       while(c!='#'||GetTop(OPTR)!='#') 
       if(!In(c)) { m=atoi(&c); Push(&OPND,m); c = *ptr++; } 
       else switch(Precede(GetTop(OPTR),c)) { 
            case '<': Push(&OPTR,c); c = *ptr++; break; 
            case '=': x=Pop(&OPTR); c = *ptr++; break; 
            case '>': theta=Pop(&OPTR); b=Pop(&OPND); a=Pop(&OPND); Push(&OPND,Operate(a,theta,b)); break;
             } 
	   return GetTop(OPND); 
   }
   //判断输入的表达式是否合法 
   int IsLaw(){
	  char *e=expr;
      char c=*e++;
	  int i=0,j=0,k=0,h=0;
	  while(c!='#'){ 
          if(!In(c)){
		    i++;c = *e++; //计数操作数的个数 
		  }
		  else if(c!='('&&c!=')') {
		    j++;c = *e++;  //计数'+'、'-'、'*'、'/'的个数 
		  }
		  else if(c=='('){
		    k++;c = *e++; //计数左括号的个数 
		  }else {
		    h++;c = *e++;  //计数右括号的个数 
		  }
	  }
	  
	  if(i==j+1&&k==h){ 
		  return 1;
	  }
	   else 
		   return 0;
   }
   int ConsOperate(){
      InitStack(&OPTR, "OPTR"); //初始化运算符栈 
      Push(&OPTR,'#'); //将#压入运算符栈 
      InitStack(&OPND, "OPND"); // 初始化操作数栈  
      printf("\n\n结果是:%d\n", EvalExpr());
	  return 1; 
   }
   int main(void) {
	   int i=1;
	   printf("请输入算术表达式以 \"#\" 号结束:"); 
       do{ gets(expr); }while(!*expr); 
	   if(IsLaw()==1){
        ConsOperate();
	   }else {
		   printf("你输入了一个错误的表达式!\n请重新输入一个正确的算术表达式!\n");
		   do{ gets(expr); }while(!*expr); 
		   if(IsLaw()==1){
		    ConsOperate(); 
		   }else {
			   printf("你还是输入错误!\n操作结束!");
			   return 0;
		   }
	       return 0;
	   }
	   system("pause");
	   return 0;
   } 
   

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -