#include <iostream>
#include <map>
#define Max_size 100
using namespace std;
typedef struct
{
char elem[Max_size];
int length;
}char_stack;
typedef struct
{
int elem[Max_size];
int length;
}int_stack;
int index (char c)
{
if (c=='+') return 0;
else if (c=='-') return 1;
else if (c=='*') return 2;
else if (c=='/') return 3;
else if (c=='(') return 4;
else if (c==')') return 5;
else
return 6;
}
int value[7][7]={{1,1,-1,-1,-1,1,1},
{1,1,-1,-1,-1,1,1},
{1,1,1,1,-1,1,1},
{1,1,1,1,-1,1,1},
{-1,-1,-1,-1,-1,0,0},
{1,1,1,1,0,1,1},
{-1,-1,-1,-1,-1,0,0}};
void init_optr(char_stack &s)
{
s.length=0;
}
void init_opnd(int_stack &s)
{
s.length=0;
}
void push_optr(char_stack &s,char c)
{
s.elem[s.length++]=c;
}
void push_opnd(int_stack &s,int n)
{
s.elem[s.length++]=n;
}
char pop_optr(char_stack &s)
{
return s.elem[--s.length];
}
int pop_opnd(int_stack &s)
{
return s.elem[--s.length];
}
char get_optr(char_stack s)
{
return s.elem[s.length-1];
}
int cal(int a,int b,char c)
{
int sum;
switch (c){
case '+':sum=a+b;break;
case '-':sum=a-b;break;
case '*':sum=a*b;break;
case '/':sum=a/b;break;
}
return sum;
}
int infix_cal(string s)
{
char_stack optr;
int_stack opnd;
init_optr(optr);
init_opnd(opnd);
push_optr(optr, '#');
char topoptr, c;
int num = 0, a, b, i = 0;
topoptr = get_optr(optr);
while(s[i] != '#' || topoptr != '#')
{
if (s[i] >= '0' && s[i] <= '9')
{
num = 0;
while (s[i] >= '0' && s[i] <='9')
{
num = num * 10 + s[i] -'0';
i++;
}
push_opnd(opnd, num);
}
else
{
if (value[index(get_optr(optr))][index(s[i])] == 1)
{//栈顶元素优先级大于当前待入栈的元素,所以要将数字栈中的元素弹出进行运算
c = pop_optr(optr);
b = pop_opnd(opnd);
a = pop_opnd(opnd);
push_opnd(opnd, cal(a, b, c));
}
else if(value[index(get_optr(optr))][index(s[i])] == 0)
{//栈顶元素优先级和当前待入栈元素的优先级相等,即'('与‘)’
c = pop_optr(optr);
i++;
}
else//栈顶元素优先级小于待入栈元素,则继续入栈
push_optr(optr, s[i++]);
}
topoptr = get_optr(optr);
}
return pop_opnd(opnd);
}
int prefix_cal(string s)
{//前缀表达式的计算
//将表达式从后往前扫描,遇到数字就压栈,遇到运算符就将数字出栈参与运算
//eg 1 + 2 * 3 + 4 * 5 -------> + + 1 * 2 3 * 4 5 可以看出,符号越在后面出现,符号参与运算的级别越高
int_stack opnd;
init_opnd(opnd);
int length = s.length()-1, a, b, num;
while(length >= 0)
{
if (s[length] >='0' && s[length] <= '9')
{
int k = 1;
num = 0;
while(s[length] >= '0' && s[length] <= '9')
{
num = num + k * (s[length--] - '0');
k = k * 10;
}
push_opnd(opnd, num);
}
else
{
a=pop_opnd(opnd);
b=pop_opnd(opnd);
push_opnd(opnd, cal(a, b ,s[length--]));
}
length--;
}
return pop_opnd(opnd);
}
int suffix_cal(string s)
{//后缀表达式的计算
//从前往后扫描,遇到数字就压栈,遇到运算符就将数字出栈参与运算
//eg 1 + 2 * 3 + 4 * 5 -------> 1 2 3 * + 4 5 * + 可以看出运算符越在前面出现,就越应该在前面参与运算
int_stack q;
init_opnd(q);
int i = 0, a, b, num = 0;
while(i<s.length())
{
if(s[i]>='0'&&s[i]<='9')
{
num = 0;
while(s[i] >= '0' && s[i] <= '9')
{
num = 10 * num + s[i++] - '0';
}
push_opnd(q,num);
}
else
{
b=pop_opnd(q);
a=pop_opnd(q);
push_opnd(q,cal(a,b,s[i++]));
}
i += 1;
}
return pop_opnd(q);
}
string infix_suffix(string s)
{//中缀转后缀
//遇到数字就输出,遇到运算符,
//若当前运算符优先级小于栈顶元素,则将栈顶元素弹出并输出
//若当前运算符优先级大于栈顶元素,则将当前运算符压入栈
//若当前运算符优先级等于栈顶元素,则将栈顶元素弹出即可
string suffix = "";
char_stack optr;
init_optr(optr);
push_optr(optr,'#');
for(int i=0,j=0;i<s.length();)
{
if(s[i]>='0'&&s[i]<='9')
{
while(s[i] >= '0' && s[i] <= '9')
{
suffix = suffix + s[i++];
}
suffix = suffix + ' ';
}
else
{
while (value[index(get_optr(optr))][index(s[i])]==1)
{
suffix = suffix + pop_optr(optr);
suffix = suffix + ' ';
}
if(value[index(get_optr(optr))][index(s[i])]==0)
{
pop_optr(optr);
i++;
}
else
push_optr(optr,s[i++]);
}
}
while (get_optr(optr) != '#')
{
suffix = suffix + pop_optr(optr) +' ';
}
return suffix;
}
string infix_prefix(string s)
{
//中缀转前缀
//
string prefix = "";
char_stack p,q;
init_optr(p);
init_optr(q);
push_optr(p,'#');
push_optr(q,'#');
for (int i=s.length()-1;i>=0;)
{
char c = s[i];
if(s[i]>='0'&&s[i]<='9')
{
while(s[i] >= '0' && s[i] <= '9')
{
c = s[i];
push_optr(q, s[i--]);
}
push_optr(q,' ');
}
else
{
while(value[index(s[i])][index(get_optr(p))]==-1)
{//当前元素小于栈顶元素的优先级,则将栈顶元素弹出,并压入数字栈
push_optr(q,pop_optr(p));
push_optr(q,' ');
}
if (value[index(s[i])][index(get_optr(p))]==0)
{//当前元素等于栈顶元素的优先级,则将栈顶元素弹出
pop_optr(p);
i--;
}
else//当前元素大于栈顶元素的优先级,则将当前元素压入栈
push_optr(p,s[i--]);
}
}
while(get_optr(p) != '#')
{//将剩余的符号压入数字栈中
push_optr(q,pop_optr(p));
push_optr(q,' ');
}
while(get_optr(q) != '#')
{//最后将数字栈中的元素全部输出即为结果
prefix = prefix + pop_optr(q);
}
return prefix;
}
int main()
{
string infix,prefix,suffix;
cin>>infix;
cout<<infix_cal(infix)<<endl;
cin>>infix;
prefix = infix_prefix(infix);
cout<<"prefix:"<<prefix<<endl;
cout<<prefix_cal(prefix)<<endl;
suffix = infix_suffix(infix);
cout<<"suffix:"<<suffix<<endl;
cout<<suffix_cal(suffix)<<endl;
return 0;
}