1. 程式人生 > >棧的基本操作及其應用 表示式求值

棧的基本操作及其應用 表示式求值

輸入一個表示式求結果

因為程式的限制數的大小有限制

#include<stdio.h>
#include<iostream> 
#include<cstdio>
#include<stdlib.h>  
#include<string.h>
#include<string>
using namespace std;
#define MAXSIZE 100
#define OK 1
#define ERROR 0
#define OVERFLOW -1

typedef char SElemType;
typedef int Status;

typedef struct
{
	SElemType *base;  //棧底指標 
	SElemType *top;   //棧頂指標 
	int stacksize;   //棧可用最大容量 
}SqStack;

//構造一個空棧
Status InitStack (SqStack &S) 
{ 
	S.base = new SElemType[MAXSIZE];   //為順序棧動態分配一個最大容量為MAXSIZE的陣列空間 
	if(!S.base )  exit(OVERFLOW);      //儲存分配失敗 
	S.top=S.base ;                     // top初始base,空棧 
	S.stacksize = MAXSIZE;             //stacksize置為最大容量MAXSIZE 
	return OK;	
}

//入棧 
Status Push(SqStack &S,SElemType e)
{//插入新的棧頂元素 e 
 	if(S.base - S.top == S.stacksize )  return ERROR;   //棧空 
	*S.top ++ = e;                         //e壓入棧列,棧頂指標加1 
	return OK;
} 

//出棧 
Status Pop(SqStack &S,SElemType &e)
{//插入新的棧頂元素 e 
 	if(S.base == S.top )  return ERROR;   //棧空 
	e = *--S.top;                         //棧頂指標減1 ,將棧頂元素賦給e 
	return OK;
}

//取棧頂元素 
SElemType GetTop(SqStack S)
{//插入新的棧頂元素 e  
 	if(S.base != S.top )    //棧非空 
	   return *(S.top - 1);    //返回棧頂元素,棧頂指標不變 
}

//In
int In(char x1)
{
	if( x1 =='(' || x1 ==')' || x1 =='+' || x1 =='-' || x1=='*' || x1=='/' || x1=='#')
	 return OK;
	else 
	 return ERROR;
} 

char Operate(char i, char th,char j)   //運算函式 
{
	char k;
	i = i -'0';
	j = j -'0';
	switch( th )
	{
		case '+':
			k = i+j+'0';
		case '-':
			k = i-j+'0';
		case '*':
			k = i*j+'0';
		case '/':
			k = i/j+'0';
	}
	return k;
}

char Precede( char a,char b)   //比較優先順序 
{
	switch( a )   
	{
		case '+':
		  if( b == '+' || b == '-' || b == ')' || b == '#') 
		       return '>';
		  else if(b == '*' || b == '/' || b == '(')	
		       return '<';
		    break;
		 
		case '-':
		  if( b == '+' || b == '-' || b == ')'|| b == '#' ) 
		       return '>';
		  else if( b == '('|| b == '*' || b == '/' )	
		       return '<';
		   break;
		  	
		case '*':
	      if( b == '+' || b == '-' || b == ')'|| b == '#' || b == '*' || b == '/' )
		     return '>';
		  else if( b == '(')	
		     return '<';
		   break;
		  
		case '/':
		  if( b == '+' || b == '-' || b == ')'|| b == '#' || b == '*' || b == '/' )
		     return '>';
		  else if( b == '(')	
		     return '<';
		  break;
		  
		case '(':
		  if( b == ')')
		     return '=';
		  else if( b == '+' || b == '-' || b == '('|| b == '*' || b == '/')
		     return '<';
		  break;
		  
		case ')':
		  if( b == '+' || b == '-' || b == ')'|| b == '#' || b == '/' || b == '*')
		      return '>';	
		   break;
		  
		  
	    case '#':
	      if( b == '#')
	         return '=';
	      else if(b == '+' || b == '-' || b == '('|| b == '#' || b == '/' || b == '*')
		     return '<';
			break;	
	}
	
}

//表示式求值
char EvaluateExpersion()
{//算數表示式求值的算符優先演算法,設OPTR和OPND分別為運算子棧和操作符棧 
    SElemType ch;
    SqStack OPTR;
    SqStack OPND;
     char x; 
    
	InitStack(OPTR);   //初始化OPTR棧 
	InitStack(OPND);   //初始化OPND棧 
	
    Push(OPTR,'#');    //將表示式起始符“# ”入OPTR棧 
    cin>>ch;
    
    char theta,a,b;
    
	while( ch!='#' || GetTop(OPTR) != '#' )    //表示式沒有掃描完畢或者OPTR的棧頂元素不為“# ” 
	{
		if( !In(ch) )                      //ch不是運算子則進OPND棧 
		{
		  Push(OPND,ch);
		  cin>>ch;
		}
		else
		 switch( Precede( GetTop(OPTR),ch) )     //比較棧頂元素和ch的優先順序 
		 {
		 	case '<':
		 		Push(OPTR,ch);                  //將當前字元壓入OPTR棧,讀入下一字元ch 
		 		cin>>ch;
		 		break;
		    case '>':
		    	Pop(OPTR,theta);               //彈出OPTR棧頂的運算子 
		    	Pop(OPND,b);                   //彈出OPTR棧頂的兩個運算數 
		    	Pop(OPND,a);
		 		Push(OPND,Operate(a,theta,b));  //將運算結果壓入OPND棧 
		 		break;
		    case '=':               //OPTR棧的棧頂元素是”(  ”且 ch是 “) ” 
		 	    Pop(OPTR , x);            // 彈出OPTR的棧頂的“( ” ,讀入下一字元ch 
		 		cin>>ch;
		 		break;
		 }
	}
	return GetTop(OPND)-'0';          //OPND棧頂元素即表示式求值結果 
} 

int main()
{
	cout<<"表示式結果為:"<<EvaluateExpersion()<<endl;
	return 0;
}