【中缀表达式转后缀表达式&&输出计算结果】
2017-02-24 17:46
281 查看
【描述】参见NYOJ 35
/***************** Aythor:herongwei; Date:2017/2/24 17:42 ****************/ #include <iostream> #include <stdio.h> #include <stack> #include <queue> #include <vector> #include <string.h> #include <stdlib.h> #include <algorithm> using namespace std; const int maxn = 1e5+10; /* 表达式求值: 【1】将中缀表达式(标准四则运算表达式)化为后缀表达式 【2】将后缀表达式进行运算 【example】9+(3-1)*3+10/2 = 20 【算法思想】从左至右遍历中缀表达式的每个数字和符号,若是数字就输出,即成为后缀表达式的一部分; 若是符号,则判断其与栈顶元素的优先级,若是右括号或者优先级低与栈顶元素的则栈顶元素 依次出栈输出,并将当前符号进栈,一直到最后输出后缀表达式为止。 【1】 样例输入 2 1.000+2/4= ((1+2)*5+1)/4= 样例输出 1.50 4.00 */ int len; char input[maxn],ouput[maxn]; stack<char> Ope_stack,ope_tp; stack<double> Num_stack; vector<char> ans; vector<char>::iterator start, end; /* 将后缀表达式进行运算得到结果 */ int fuhao_pre(char c) { if(c == '=' || c=='(') return 0; else if(c == '+' || c=='-') return 1; else if(c == '*'|| c=='/') return 2; } void compute(stack<double>& Num_stack,stack<char>& Ope_stack) { double b =Num_stack.top(); Num_stack.pop(); double a = Num_stack.top(); Num_stack.pop(); switch(Ope_stack.top()) { case '+': Num_stack.push(a+b); break; case '-': Num_stack.push(a-b); break; case '*': Num_stack.push(a*b); break; case '/': Num_stack.push(a/b); break; } Ope_stack.pop(); } int z_z_h(char input[]) { while(!ope_tp.empty()) ope_tp.pop(); ans.clear(); ope_tp.push('='); ///结束标志 scanf("%s",input); ///9+(3-1)*3+10/2 len=strlen(input); for(int i=0; i<len; ++i) { if( isdigit(input[i]) )///操作数直接存入ans { ans.push_back(input[i]); } ///左括号入栈 else if(input[i]=='(') { ope_tp.push(input[i]); } else if(input[i]==')') ///右括号,将匹配的左括号内容存入Ope_stack,左括号出栈 { while(ope_tp.top()!='(') { ans.push_back(ope_tp.top()); ope_tp.pop(); } ope_tp.pop(); } else if( (ope_tp.empty()) || fuhao_pre(input[i])>fuhao_pre(ope_tp.top()) )///当前元素优先级大于栈顶元素则入栈 ope_tp.push(input[i]); else ///当前元素优先级小于栈顶元素 { while((ope_tp.empty()) || fuhao_pre(input[i])<=fuhao_pre(ope_tp.top()) ) /// 注意<=,若没有比当前元素更低的优先级,则全部出栈 { ans.push_back(ope_tp.top()); ope_tp.pop(); } ope_tp.push(input[i]); } } while(ope_tp.top() != '=') ///其余操作符存入后缀表达式中 { ans.push_back(ope_tp.top()); ope_tp.pop(); } puts("/****中缀表达式转后缀表达式****/"); for(start = ans.begin(), end = ans.end(); start < end; ++start) printf("%c", *start); printf("\n"); } int solve(char input[]) { scanf("%s",input); ///9+(3-1)*3+10/2 len=strlen(input); while(!Ope_stack.empty()) Ope_stack.pop(); ans.clear(); for(int i=0; i<len; ++i) { if( isdigit(input[i]) )///操作数直接存入ans { double tp=atof(&input[i]); while(i<len && (isdigit(input[i]) || input[i]=='.')) ++i; i--; Num_stack.push(tp); } else ///当前元素优先级小于栈顶元素 { if(input[i] == '(') Ope_stack.push(input[i]); else if(input[i] == ')') { while(Ope_stack.top()!='(') compute(Num_stack,Ope_stack); Ope_stack.pop(); } else if(Ope_stack.empty() || fuhao_pre(input[i])>fuhao_pre(Ope_stack.top())) Ope_stack.push(input[i]); else { while(!Ope_stack.empty() && fuhao_pre (input[i])<=fuhao_pre(Ope_stack.top())) compute(Num_stack,Ope_stack); Ope_stack.push(input[i]); } } } puts("/****后缀表达式计算结果****/"); Ope_stack.pop(); printf("%.2f\n",Num_stack.top()); Num_stack.pop(); } int main() { freopen("in.txt","r",stdin); int T,len; scanf("%d",&T); getchar(); while(T--) { // z_z_h(input); // 中缀表达式转后缀表达式 solve(input); //后缀表达式求出结果 } return 0; } cong 神的代码: ////运行时间:2010-10-07 10:18:39 | 运行人:张云聪 // //#include <vector> //#include <string> //#include <iostream> //#include<stdio.h> //#include<string> //using namespace std; // //char DATA[7][7]= //{ // {'>','>','<','<','<','>','>'}, // {'>','>','<','<','<','>','>'}, // {'>','>','>','>','<','>','>'}, // {'>','>','>','>','<','>','>'}, // {'<','<','<','<','<','=',' '}, // {'>','>','>','>',' ','>','>'}, // {'<','<','<','<','<',' ','='} //}; //int f(char a) //{ // switch(a) // { // case '+': // return 0; // case '-': // return 1; // case '*': // return 2; // case '/': // return 3; // case '(': // return 4; // case ')': // return 5; // case '=': // return 6; // default: // printf("f error"); // } //} //char Precede(char a,char b) //{ // return DATA[f(a)][f(b)]; //} //double operate(double a,char theta,double b) //{ // // switch(theta) // { // case '+': // return a+b; // break; // case '-': // return a-b; // case '*': // return a*b; // case '/': // return a/b; // default : // printf("operate error"); // } //} //string str; //vector<char> OPTR;//操作符 //vector<double> OPND; //操作数 //int main(int argc, char* argv[]) //{ // // int nn; // cin>>nn; // while(nn--) // { // str.clear(); // OPTR.clear(); // OPND.clear(); // cin>>str; // OPTR.push_back('='); // int i=0,flag=0;//flag=1代表上次是一个数。 // double temp; // while(i!=str.size()) // { // if ((str[i]<='9'&&str[i]>='0'||str[i]=='.')&&flag==0) // { // sscanf(&str[i],"%lf",&temp); // OPND.push_back(temp); // flag=1; // } // else if((str[i]>'9'||str[i]<'0')&&str[i]!='.') // { // flag=0; // double a,b; // char theta; // // switch (Precede(OPTR.back(),str[i])) // { // case '<': // OPTR.push_back(str[i]); // break; // case '=': // OPTR.pop_back(); // break; // case '>': // theta=OPTR.back(); // OPTR.pop_back(); // b=OPND.back(); // OPND.pop_back(); // a=OPND.back(); // OPND.pop_back(); // OPND.push_back(operate(a,theta,b)); // i--; // break; // // default: // break; // } // } // i++; // } // // printf("%.2lf\n",OPND.back()); // } // return 0; // // //} //
相关文章推荐
- 中缀表达式转后缀表达式并输出计算结果
- 输入一个表达式,没有括号,数字小于0-9之间,输出计算结果,所有的中间结果化为整形。 例如: 输入:3+8×2/9-2 输出:2
- 第九周【项目1】在第8周项1的基础上(1)再定义一目运算符 -,-c相当于0-c(2)定义Complex类中的<<和>>运算符的重载,实现输入和输出,改造原程序中对运算结果显示方式,使程序读起来更自然
- /*输入1 个正整数 n(n<=100),计算并输出1+1/2+1/3+……+1/n。*/
- datatable的自定义配置-输出结果&排序&跳转指定页码
- 编写一个在1,2,…,9(顺序不能变)数字之间插入+或-或什么都不插入,使得计算结果总是100的程序,并输出所有的可能性。
- printf("%d",5.01)和printf("%f",5)的输出结果
- oracle的结果输出单引号 ' 的字符 的sql语句
- 用@”a string“的形式,例如要求输出结果为the third is "c" !
- 编写一个在1,2,…,9(顺序不能变)数字之间插入+或-或什么都不插入,使得计算结果总是100的程序,并输出所有的可能性。
- 编写一个在1,2,…,9(顺序不能变)数字之间插入+或-或什么都不插入,使得计算结果总是 100 的程序,并输出所有的可能性
- php 结果输出到excel
- 中缀表达式转换为后缀表达式&后缀表达式的计算
- ZOJ1083:Frame Stacking(拓扑排序 & 字典序输出所有结果)
- 2. 计算出1900年1月1日至当前日期之间总共间隔多少天,将其除以7取余数,该结果即为当月第一天是星期几,按日历格式输出
- 给定一个正整数,编写程序计算有多少对质数的和等于输入的这个正整数,并输出结果。
- DateTime.Now.ToString("yyyy/MM/dd") 输出的结果是 2006-03-16
- HDU 3729 I'm Telling the Truth(二部图最大匹配+结果输出)
- 使用Messenger 从Activity发送数据到service 通过后台计算结果Log输出;
- 编一个程序,从 string 对象中去掉标点符号。要求输入到程序的字符串必须含有标点符号,输出结果则是去掉标点符号后的 string 对象。