定义俩个栈,一个字符栈,一个数字栈(扩大运算范围,用数字栈比字符栈好),输入为一个字符串,以‘=’结尾,输出为运算结果,代码如下:
#include <stdio.h>
#include<malloc.h>
#include<math.h>
typedef int ElemType;
typedef char SElemType;
#define maxsize 30
#define Maxsize 30
typedef struct {
ElemType* base;
ElemType* top;
int size;
}SqStackInt, * ListStackInt; //数字栈
typedef struct {
SElemType* base;
SElemType* top;
int size;
}SqStack, * ListStack;//字符栈
void StackInitInt(ListStackInt& S) {
S = (ListStackInt)malloc(sizeof(SqStackInt));
S->base = (ElemType*)malloc(maxsize * sizeof(ElemType));
S->top = S->base;
S->size = maxsize;
}
void StackPushInt(ListStackInt S, ElemType e) {
if (S->base == S->top - S->size)
{
return;
}
*S->top++ = e;
}
ElemType StackPopInt(ListStackInt S) {
if (S->base == S->top) return 0;
ElemType e;
e = *(--S->top);
return e;
}
void StackDisplayInt(ListStackInt S) {
for (ElemType* i = S->base; i < S->top; i++)
{
printf("%d ", *i); //字符修改
}
}
ElemType StackGetInt(ListStackInt S) {
if (S->base == S->top) { return 0; }
else { return *(S->top - 1); }
}
//数字栈的基础操作
void StackInit(ListStack& S) {
S = (ListStack)malloc(sizeof(SqStack));
S->base = (SElemType*)malloc(Maxsize * sizeof(SElemType));
S->top = S->base;
S->size = Maxsize;
}
void StackPush(ListStack S, SElemType e) {
if (S->base == S->top - S->size)
{
return;
}
*S->top++ = e;
}
SElemType StackPop(ListStack S) {
if (S->base == S->top) return 0;
SElemType e;
e = *(--S->top);
return e;
}
void StackDisplay(ListStack S) {
for (SElemType* i = S->base; i < S->top; i++)
{
printf("%c ", *i);
}
}
SElemType StackGet(ListStack S) {
if (S->base == S->top) { return 0; }
else { return *(S->top - 1); }
}
//字符栈的基础操作
int IfDigtal(SElemType s) {//判断当前字符是否为数字
switch (s)
{
case '0': return 0;break;
case '1': return 1;break;
case '2': return 2;break;
case '3': return 3;break;
case '4': return 4;break;
case '5': return 5;break;
case '6': return 6;break;
case '7': return 7;break;
case '8': return 8;break;
case '9': return 9;break;
default: return 10; break;
}
}
int contrast(char symbol) { //生成比较数组的索引
switch (symbol)
{
case '+':return 1;break;
case '-':return 2;break;
case '*':return 3;break;
case '/':return 4;break;
case '(':return 5;break;
case ')':return 6;break;
case '=':return 7;break;
default:return 0;break;
}
}
int compare(char Symboltop, char Symboljoin) {//比较优先级
int topdata;//栈顶元素
int joindata;//新加入的元素
int prior[8][8] = { {0,0,0,0,0,0,4,0},
{0,1,1,0,0,0,1,1},
{0,1,1,0,0,0,1,1},
{0,1,1,1,1,0,1,1},
{0,1,1,1,1,0,1,1},
{0,0,0,0,0,0,3,4},
{0,1,1,1,1,4,1,1},
{0,4,4,4,4,4,4,4} };
topdata = contrast(Symboltop);
joindata = contrast(Symboljoin);
return prior[topdata][joindata];
}
int get(SElemType** Formula, int n) { //取连续数字,二重指针推进字符遍历,n为字符长度
int data = 0;
int count = 0;
while (IfDigtal(**Formula)!=10)
{
(*Formula)++;
count++;
}//找到有限数字
for ( int j = count; j >0; j--)
{
(*Formula)--;
}//计算数字长度
for (count; count>0; count--)
{
data += IfDigtal (**Formula)* pow(10, count - 1);
(*Formula)++;
}//生成数字,接着返回
return data;
}
int calculation(int data1, int data2, char data3) {//计算,前面俩个是计算数字,后面一个是计算符号
switch (data3)
{
case'+':return data1 + data2;break;
case'-':return data1 - data2;break;
case'*':return data1 * data2;break;
case'/':return data1 / data2;break;
default:
break;
}
}
void Computation(SElemType *Formula,int n){//输入字符,生成结果并打印
ListStack C;StackInit(C);ListStackInt S;StackInitInt(S);
while (*Formula!='\0')//遍历
{
if (IfDigtal(*Formula)!=10)//当前符号为数字,则取出连续数字为一个数
{
StackPushInt(S, get(&Formula,n));
}
else if(IfDigtal(*Formula) == 10)//当前符号为字符
{
switch (compare(StackGet(C), *Formula))//判断优先级
{
case 0://优先级高,入栈,字符指针前进
StackPush(C, *Formula);
Formula++;
break;
case 1://优先级低,字符栈退栈,数字栈退栈,进行计算
StackPushInt(S, calculation(StackPopInt(S), StackPopInt(S), StackPop(C)));break;
case 3://优先级相同,退栈,字符指针前进
StackPop(C);
Formula++;
break;
}
}
StackDisplay(C);//打印字符栈遍历每一层的结果
printf("\n");
StackDisplayInt(S);//打印数字栈遍历每一层的结果
printf("\n\n");
}
StackDisplayInt(S);//打印最后计算结果
}
int main(){
char *data = "(12+12)*12-1/15=";
Computation(data, 20);
return 0;
}