Problem Description
对于一个基于二元运算符的算术表达式,转换为对应的后缀式,并输出之。
Input
输入一个算术表达式,以‘#’字符作为结束标志。
Output
输出该表达式转换所得到的后缀式。
Sample Input
ab+(c-d/e)f#
Sample Output
abcde/-f+
题解:
根据一般算术表达式转换成后缀式的规则,在用代码实现时,需要将原表达式遍历一遍,可以具体分为以下几种情况:
当碰到字母时,直接输出,作为后缀式的一部分。
当碰到运算符+ -*/的时候就要分情况讨论,若此时栈为空,运算符直接入栈。若此时栈不空,这个运算符就要和栈顶的运算符进行级别高低的比较,若这个运算符级别高于栈顶运算符,则入栈,否则栈顶运算符出栈,这个运算符再入栈。(这样操作是为了做到遵循运算法则先乘除后加减,先运算级别高的运算符所在的式子,并且先左后右计算)。
当碰到括号时,若为左括号,直接入栈,若为右括号,则把栈内直到左括号的元素依次输出。
当碰到‘#’时说明原表达式遍历完了,此时若栈内还有元素,则栈内的元素依次出栈。
#include <stdio.h>
#include <stdlib.h>
#define stackinitsize 100
#define stackcreat 10
#define ok 1
#define overflow -1
#define error -1
typedef int elemtype;
typedef struct
{
elemtype *base;
elemtype *top;
int stacksize;
} sqstack;
int initstack(sqstack *s)
{
s->base=(elemtype*)malloc(stackinitsize*sizeof(elemtype));
if(!s->base)exit(overflow);
s->top=s->base;
s->stacksize=stackinitsize;
return ok;
}
int push(sqstack *s,elemtype e)
{
if(s->top-s->base>=s->stacksize)
{
s->top=(elemtype*)realloc(s->base,(s->stacksize+stackcreat)*sizeof(elemtype));
if(!s->base)exit(overflow);
s->top=s->base+s->stacksize;
}
*s->top++=e;
return ok;
}
int pop(sqstack *s)
{
if(s->top==s->base)return error;
s->top--;
return ok;
}
int stackempty(sqstack *s)
{
if(s->top==s->base)return 1;
else return 0;
}
char gettop(sqstack *s)
{
char e;
if(s->top==s->base)return error;
e=*(s->top-1);
return e;
}
int bijiao(char a,char b)//用于比较运算符优先级高低的函数
{
if(((a=='*'||a=='/')&&(b=='+'||b=='-'))||((a=='+'||a=='-')&&(b=='+'||b=='-'))||((a=='*'||a=='/')&&(b=='*'&&b=='/')))
return 1;
else return 0;
}
int main()
{
char c,e;
sqstack s;
initstack(&s);
while(scanf("%c",&c)!=EOF)
{
if(c!='#')
{
if(c>='a'&&c<='z')printf("%c",c);//如果是字符直接输出
else if(c=='+'||c=='-'||c=='*'||c=='/')//如果是运算符要分情况
{
if(stackempty(&s))push(&s,c);//如果栈为空,直接入栈
else
{
e=gettop(&s);
if(bijiao(e,c)==1)//输入的运算符不比栈顶运算符级别高
{
printf("%c",e);//输出栈顶运算符
pop(&s);//栈顶运算符出栈
push(&s,c);//输入的运算符入栈
}
else push(&s,c);//直接入栈
}
}
else if(c=='('||c==')')//为括号的情况
{
if(c=='(')push(&s,c);
if(c==')')
{
e=gettop(&s);
while(e!='(')
{
printf("%c",e);
pop(&s);
e=gettop(&s);
}
if(e=='(')pop(&s);
}
}
}
if(c=='#')//最后把剩余的元素输出
{
while(!stackempty(&s))
{
e=gettop(&s);
printf("%c",e);
pop(&s);
}
printf("\n");
break;
}
}
return 0;
}