用栈解决表达式的计算问题
1.首先要有两个栈一个操作数栈一个运算符栈;
2.设置表达式的结束符是#,预设运算符
3.若当前字符是操作数,则直接压入操作数栈
4.若当前字符是运算符,且运算符的优先级高于栈顶运算符则进栈,否则从操作数栈中弹出两个操作数并弹出运算符栈的栈顶运算符,经计算后,将结果压入操作数栈。
//操作数栈
typedef struct{
float an[20];
int topn;
}OPRD;
//运算符栈
typedef struct{
char ac[20];
int topc;
}OPTR;
在做的过程中有以下几个问题吧:
问题一:如何把输入的字符转化为浮点型
wb = wb + ((float)love[i-n]-48) * (power(10,n-1));
用到了一个类型转化符,里面的power()函数是一个求指数的函数;具体代码如下:
//求指数
int power(int a , int b)
{
int i=0;
int wb=1;
for(;i<b;i++)
wb *= a;
return wb;
}
问题二:如果输入的是‘2’‘1’,怎么让他读入21;
n=0
if(love[i]>='0' && love[i]<='9')
{
while(love[i]>='0' && love[i]<='9')
{
n++;
i++;
}
while(n!=0)
{
wb = wb + ((float)love[i-n]-48) * (power(10,n-1));
n--;
}
}
问题三:如果是小数怎么办
if(love[i] == '.')
{
i++;
while(love[i]>='0' && love[i]<='9')
{
n++;
i++;
}
while(n!=0)
{
wb = wb + ((float)love[i-n]-48) / (power(10,n));
n--;
}
}
问题四:运算符的比较
就是用switch函数对两个运算符进行比较通过返回值判断大小具体函数在下面;
下面放完整代码
#include <stdio.h>
#include <string.h>
#include <math.h>
#include <stdlib.h>
//操作数栈
typedef struct{
float an[20];
int topn;
}OPRD;
//运算符栈
typedef struct{
char ac[20];
int topc;
}OPTR;
//字符串输入函数
char *s_gets(char *a , int n)
{
char *b;
int i=0;
b= fgets(a,n,stdin);
if(b)
{
while(a[i]!='\n' && a[i]!='\0')
i++;
if(a[i]=='\n')
a[i]='\0';
else
while(getchar()!='\n')
continue;
}
return b;
}
//求指数
int power(int a , int b)
{
int i=0;
int wb=1;
for(;i<b;i++)
wb *= a;
return wb;
}
//操作数入栈函数
int push_n(OPRD *s , float x)
{
if(s->topn == 19)
return 0;
else
s->an[++s->topn] = x;
return 1;
}
//运算符的比较
int bijiao(char a , char b)
{
switch(a)
{
case '+':
{
switch(b)
{
case '+':return 0;
case '-':return 0;
case '*':return 1;
case '/':return 1;
case '(':return 1;
case ')':return 0;
case '#':return 0;
default:break;
}
}
case '-':
{
switch(b)
{
case '+':return 0;
case '-':return 0;
case '*':return 1;
case '/':return 1;
case '(':return 1;
case ')':return 0;
case '#':return 0;
default:break;
}
}
case '*':
{
switch(b)
{
case '+':return 0;
case '-':return 0;
case '*':return 0;
case '/':return 0;
case '(':return 1;
case ')':return 0;
case '#':return 0;
default:break;
}
}
case '/':
{
switch(b)
{
case '+':return 0;
case '-':return 0;
case '*':return 0;
case '/':return 0;
case '(':return 1;
case ')':return 0;
case '#':return 0;
default:break;
}
}
case '(':
{
switch(b)
{
case '+':return 1;
case '-':return 1;
case '*':return 1;
case '/':return 1;
case '(':return 1;
default:break;
}
}
case ')':
{
switch(b)
{
case '+':return 0;
case '-':return 0;
case '*':return 0;
case '/':return 0;
case ')':return 0;
case '(':return 2;
case '#':return 0;
default:break;
}
}
case '#':
{
switch(b)
{
case '+':return 1;
case '-':return 1;
case '*':return 1;
case '/':return 1;
case '(':return 1;
case '#':return 2;
default:break;
}
}
}
}
//操作数出栈
int popn(OPRD *s , float *x)
{
if(s->topn == -1)
return 0;
else
*x = s->an[s->topn--];
return 1;
}
//运算符出栈
int popc(OPTR *s , char *x)
{
if(s->topc == -1)
return 0;
else
*x = s->ac[s->topc--];
return 1;
}
//判断运算符栈空
int kong_c(OPTR *s)
{
if(s->topc == -1)
return 0;
else
return 1;
}
int main()
{
OPTR *s;
OPRD *p;
int k,i,n;
i=0;
n=0;
float wb=0;
char ch;
char love[40];
float a,b;
s = (OPTR*)malloc(sizeof(OPTR));
p = (OPRD*)malloc(sizeof(OPRD));
s->topc = -1;
printf("%d",s->topc);
p->topn = -1;
printf("输入以#开头以#结尾的表达式:\n");
s_gets(love,40);
k = strlen(love);
for(;i<k;)
{
wb=0;
if(love[i]>='0' && love[i]<='9')
{
while(love[i]>='0' && love[i]<='9')
{
n++;
i++;
}
while(n!=0)
{
wb = wb + ((float)love[i-n]-48) * (power(10,n-1));
n--;
}
if(love[i] == '.')
{
i++;
while(love[i]>='0' && love[i]<='9')
{
n++;
i++;
}
while(n!=0)
{
wb = wb + ((float)love[i-n]-48) / (power(10,n));
n--;
}
}
push_n(p,wb);
}
else
{
if(kong_c(s) == 0 || love[i]=='(')
{
push_c(s,love[i]);
i++;
}
else
{
getac(s,&ch);
while(bijiao(ch,love[i])!=1 && bijiao(ch,love[i])!=2)
{
popc(s,&ch);
popn(p,&a);
popn(p,&b);
switch(ch)
{
case '+':wb = b + a;break;
case '-':wb = b - a;break;
case '*':wb = b * a;break;
case '/':wb = b / a;break;
case ')':break;
default:break;
}
push_n(p,wb);
getac(s,&ch);
}
if(bijiao(ch,love[i])==2)
{
popc(s,&ch);
i++;
}
else if(bijiao(ch,love[i])==1)
{
push_c(s,love[i]);
i++;
}
}
}
}
popn(p,&wb);
printf("结果是%.2f\n",wb);
}