基本思路:
首先定义两个栈,一个存放数字,一个存放符号。
存放数字的栈:
只有当后面的一位是符号时才入栈,这是因为如果是一个多位数的情况。
存放符号的栈:
1.当符号栈为空或者是a[i] 不是 ‘)’并且栈顶元素是‘(’时或者符号优先级大于栈顶元素的优先级时入栈。
2.当a[i] 是 ‘)’并且栈顶元素是‘(’时,弹出栈顶元素,即括号成对了,把左括号删除。
3.当a[i] 是 ‘)’并且栈顶元素不是‘(’时或者符号优先级小于等于栈顶元素的优先级时或者表达式结束,但是符号栈不为空时进行相应的加减乘除运算。
最后数字栈里只有一个元素就是最后的运算结果。
直接放代码:
#include <stdio.h>
#include <stdlib.h>
#define SUCCESS 0
#define FAILURE -1
struct node
{
int data;
struct node *next;
};
typedef struct node Node;
struct stack
{
Node *top;
int count;
};
typedef struct stack LinkStack;
int StackInit(LinkStack *S)
{
S->top = NULL;
S->count = 0;
return SUCCESS;
}
int StackPush(LinkStack *S, int e)
{
if(S == NULL)
{
return FAILURE;
}
Node *p = (Node *)malloc(sizeof(Node));
if(p == NULL)
{
return FAILURE;
}
p->data = e;
p->next = S->top;
S->top = p;
S->count++;
return SUCCESS;
}
int StackEmpty(LinkStack *S)
{
if(S == NULL)
{
return FAILURE;
}
if(S->count == 0)
{
return SUCCESS;
}
else
{
return FAILURE;
}
}
int StackGetTop(LinkStack *S)
{
if(S->top == NULL)
{
return FAILURE;
}
return (S->top->data);
}
int StackPop(LinkStack *S)
{
if(S->top == NULL)
{
return FAILURE;
}
int e;
Node *p = (Node *)malloc(sizeof(Node));
if(p == NULL)
{
return FAILURE;
}
p = S->top;
e = S->top->data;
S->top = S->top->next;
free(p);
S->count--;
return e;
}
int Priority(char c)
{
switch(c)
{
case '(':
return 3;
case '*':
case '/':
return 2;
case '+':
case '-':
return 1;
default:
return 0;
}
}
int main()
{
char a[100] = {0};
int ret, i = 0;
int temp = 0, j;
LinkStack opt, num;
if(StackInit(&num) != SUCCESS || StackInit(&opt) != SUCCESS)
{
return FAILURE;
}
printf("Please input a option:\n");
scanf("%s", a);
while(a[i] != '\0' || (StackEmpty(&opt) != SUCCESS))
{
if(a[i] >= '0' && a[i] <= '9')
{
temp = temp * 10 + a[i] - '0';
i++;
if(a[i] < '0' || a[i] > '9')
{
StackPush(&num, temp);
temp = 0;
continue;
}
}
else
{
if((StackEmpty(&opt) == SUCCESS) || (StackGetTop(&opt) == '(' && a[i] != ')') || (Priority(a[i]) > Priority(StackGetTop(&opt))))
{
StackPush(&opt, a[i]);
i++;
continue;
}
if(a[i] == ')' && StackGetTop(&opt) == '(')
{
StackPop(&opt);
i++;
continue;
}
if((a[i] == ')' && StackGetTop(&opt) != '(') || (Priority(a[i]) <= Priority(StackGetTop(&opt))) || (a[i] == '\0' && StackEmpty(&opt) != SUCCESS))
{
switch(StackPop(&opt))
{
case '+':
StackPush(&num, StackPop(&num) + StackPop(&num));
break;
case '-':
j = StackPop(&num);
StackPush(&num, StackPop(&num) - j);
break;
case '*':
StackPush(&num, StackPop(&num) * StackPop(&num));
break;
case '/':
j = StackPop(&num);
StackPush(&num, StackPop(&num) / j);
break;
default:
break;
}
continue;
}
}
}
printf("The result is %d\n", StackPop(&num));
return 0;
}