//
// main.cpp
// c++计算器
//
// Created by student on 14-5-11.
// Copyright (c) 2014年 student. All rights reserved.
//
#include<stdio.h>
#include<math.h>
#include<stdlib.h>
#define MAX 1000
struct save1
{
float n[MAX];
int top;
}stack1;
struct save2
{
char n[MAX];
int top;
}stack2;
//stack1存储数字,stack2存储运算符号.
bool stackempty(save1 s)//判断是否为空
{
if (s.top== -1)
return 1;
else
return 0;
}
bool stackempty2(save2 s)//判断是否为空
{
if (s.top== -1)
return 1;
else
return 0;
}
void push(save1 &s,float e)//将e入栈
{
if(s.top==MAX-1)
{
printf("栈已满!/n");
return ;
}
s.top++;
s.n[s.top]=e;
}
void push2(save2 &s,char e)//将e入栈
{
if(s.top==MAX-1)
{
printf("栈已满!/n");
return ;
}
s.top++;
s.n[s.top]=e;
}
void pop(save1 &s,float &e)//将栈顶元素出栈,存到e中
{
if(s.top==-1)
{
printf("栈为空!/n");
}
else
{e=s.n[s.top]; s.top--; }
}
void pop2(save2 &s,char &e)//将栈顶元素出栈,存到e中
{
if(s.top==-1)
{ printf("栈为空!/n"); }
else
{e=s.n[s.top]; s.top--; }
}
int in(char e)//e在栈内的优先级别
{
if(e=='-' || e=='+') return 2;
if(e=='*' || e=='/') return 4;
if(e=='^') return 5;
if(e=='(') return 0;
if(e==')') return 7;
return -1;
}
char precede(char ch1,char ch2)
{
char op[]="+-*/()^";
int i;
int j;
char table[7][8]={
"<<<<><<",
"<<<<><<",
">><<><<",
">><<><<",
">>>>>=>",
"<<<<=<<",
">>>>><>"
};
for (i=0; i<7; i++) if(op[i]==ch2)break;
for (j=0; j<7; j++) if(op[j]==ch1)break;
return table[i][j];
}
int out(char e)//e在栈外的优先级别
{
if(e=='-' || e=='+') return 1;
if(e=='*' || e=='/') return 3;
if(e=='^') return 6;
if(e=='(') return 7;
if(e==')') return 0;
return -1;
}
void count(float a,char ope,float b)
{
float sum;
if(ope=='+') sum=a+b;
if(ope=='-') sum=a-b;
if(ope=='*') sum=a*b;
if(ope=='/') sum=a/b;
if(ope=='^') sum=pow(a,b);
push(stack1,sum);
}
bool isdigit(char a)
{
if('0'<=a && a<='9')
return 1;
else
return 0;
}
bool isalpha(char c)
{
if (('a'<=c && c<='z') ||('A'<=c && c<='Z')) {
return 1;
}
return 0;
}
int main()
{
int i=0,len=0,j,nofpoint,g=0;//len表示输入式子的长度。 g表示读入的字符是否是字母变量、数字以及运算符。
float a,b;//a、b用来存储操作数栈中弹出的操作数,便于代入函数中进行计算。
char line[MAX],operate,temp[20];
scanf("%s",line);
while (line[len++]!='\0');
// len=(int)strlen(line);
len--;
stack1.top=-1;//将栈置为空
stack2.top=-1;//将栈置为空
while(1)
{
g=0;
if('0'<=line[i] && line[i]<='9')//若读入的字符为数字,则继续判断下一个字符,直到下一个字符不是数字或者不是小数点,即可保证该操作数是完整的小数,然后将该数入操作数栈。
{
j=0; g=1;
nofpoint=0;//记录所存的数中小数点的个数
while(('0'<=line[i] && line[i]<='9') || line[i]=='.')
{
if(line[i]=='.') nofpoint++;
temp[j++]=line[i];
i++;
if(i>=len) break;
}
if( nofpoint>1 || (i<len&&(line[i]!='-' && line[i]!='+' && line[i]!='*' && line[i]!='/' && line[i]!='^' && line[i]!=')')) )
{ printf("表达式有错\n"); return 0; }//所存数中含有不止一个小数点,或者数字后面跟的不是“+、-、*、/、^、)”,则为错误
temp[j]='\0';
b=atof(temp);
push(stack1,b);
if(i>=len) break;
}
else
{
if(line[i]=='-' || line[i]=='+' || line[i]=='*' || line[i]=='/' ||
line[i]=='^' || line[i]=='(' || line[i]==')' ) //若读入的字符为运算符的情况
{
g=1;
if(line[i]=='(' && i==len) { printf("表达式有错\n"); return 0; }// “(”放表达式最后面,错误
if(line[i]=='-' || line[i]=='+' || line[i]=='*' || line[i]=='/' || line[i]=='^')
{
if(i==len) { printf("表达式有错\n"); return 0; }//“+、-、*、/、^”放在表达式最后面,错误
if( (!isdigit(line[i+1])) && (!isalpha(line[i+1])) && line[i+1]!='(')//“+、-、*、/、^”后面跟的不是数字或者变量,错误
{ printf("表达式有错\n"); return 0; }
}
if(line[i]=='-' && (i==0 || line[i-1]=='(' ))//运算符是负号
{
push(stack1,0);
push2(stack2,line[i]);
i++;
}
else
{ //读入的运算符与运算符栈的栈顶元素相比,并进行相应的操作
if(in(stack2.n[stack2.top])<out(line[i])||stackempty2(stack2))
//if((precede(stack2.n[stack2.top], line[i])=='>')|| stackempty2(stack2))
{
push2(stack2,line[i]);i++;
}
else
if(in(stack2.n[stack2.top])==out(line[i]))
//if(precede(stack2.n[stack2.top], line[i])=='=')
{
i++; stack2.top--;
}
else
if(in(stack2.n[stack2.top])>out(line[i]))
//if (precede(stack2.n[stack2.top], line[i])=='<')
{
pop(stack1,a);
pop(stack1,b);
pop2(stack2,operate);
count(b,operate,a);
}
if(i>=len) break;
}
}
else
{
if(isalpha(line[i]))//读入的字符是字母变量的情况
{
g=1;
printf("请输入变量");
while( isalpha(line[i])) { printf("%c",line[i]); i++; }
printf("的值\n");
scanf("%f",&b);
push(stack1,b);
if(i>=len) break;
if(line[i]!='-' && line[i]!='+' && line[i]!='*' && line[i]!='/' && line[i]!='^' && line[i]!=')')//变量后面跟的不是“+、-、*、/、^、)”,则为错误
{ printf("表达式有错\n"); return 0; }
}
}
}
if(g==0) { printf("表达式有错\n"); return 0; }//g=0表示该字符是不符合要求的字符
}
while(stack2.top!=-1)//读入结束后,继续进行操作,直到运算符栈为空
{
pop(stack1,a);
pop(stack1,b);
pop2(stack2,operate);
if(operate=='(' || operate==')') //括号多余的情况
{ printf("表达式有错\n"); return 0; }
count(b,operate,a);
}
printf("%.f\n",stack1.n[stack1.top]);
return 0;
}