定义一个中缀式类,可以求其后缀式以及计算其值
来源:互联网 发布:模拟位置什么软件 编辑:程序博客网 时间:2024/05/16 15:35
- /* infix.h
- *定义一个中缀式类,可以求其后缀式,前缀式以及计算其值
- *缺点:如果算式中包含负数(如-x, x >=0),那么要写成0-|绝对值|(0-x ),才能正确求出其值;
- * 目前还没有完成求其前缀式的功能;
- *infix( string infix_str ) 构造函数,用infix_str赋值给m_infix_str
- *value( ) 求给定中缀式的值,要先调用get_postfix( )获得后缀式
- *show( ) 显示中缀式,前缀式,后缀式(待实现)
- *get_postfix( ) 获得后缀式
- *get_prefix( ) 获得前缀式(待实现)
- *
- *功能函数:
- *bool strisnum( string str ) 判断一个字符串是否表示一个float或int
- *bool strisoper( string str ) 判断一个字符串是否表示一个运算符(*,/,%,+,-)
- *把一个strisnum( )返回值为真的string转变成一个数据
- * if( strisnum( str ) )
- * {
- //float number;
- sscanf( str.c_str( ),"%f",&number);
- * }
- *本程序就是使用了istringstream,进行内存I/O来处理包含有数字的一串字符(后缀式)
- *
- *m_infix_str 存放中缀式
- *m_postfix_str 存放后缀式
- *m_prefix_str 存放前缀式
- *
- * Made by winlin 2011.4.13
- * pcliuguangtao@163.com
- * gcc 4.4.5
- */
- #include <iostream>
- #include <string>
- using std::string;
- class infix
- {
- public:
- infix( string infix_str );
- float value( );
- void show( );
- string get_postfix( );
- string get_prefix( );
- private:
- string m_infix_str;
- string m_postfix_str;
- string m_prefix_str;
- private:
- bool strisnum( string str );
- bool strisoper( string str );
- };
infix.cpp:
- #include "./infix.h"
- #include <iostream>
- #include <sstream>
- #include <stack>
- #include <string>
- #include <cstdio> //sscanf( )
- #include <cctype> //isalnum( )
- using std::string;
- using std::cout;
- using std::stack;
- using std::istringstream;
- infix::infix(string infix_str)
- {
- m_infix_str=infix_str;
- }
- string infix::get_postfix( )
- {
- char token; //从中缀式中取字符
- char topToken; //栈顶的字符
- stack<char> operStack; //stroe the opreators
- const string BLANK=" ";
- int size=m_infix_str.length( );
- for( int i=0;i<size;++i )
- {
- token=m_infix_str[ i ];
- switch( token )
- {
- case ' ':break;
- case '(':
- operStack.push( token );
- break;
- case ')':
- {
- while( 1 )
- {
- if(! operStack.empty( ) )
- {
- topToken=operStack.top( );
- operStack.pop( );
- if( topToken=='(' ) break;
- m_postfix_str.append( BLANK+topToken );
- }
- }
- }
- break;
- case '+': case '-':
- case '*': case '/': case '%':
- {
- while( 1 )
- {
- if( operStack.empty( ) || operStack.top( )=='(' ||
- (( token=='*'||token=='/'||token=='%' )&&( operStack.top( )=='+'||operStack.top( )=='-' )) )
- { //if条件包含了*/和+-之间的优先级关系
- operStack.push( token );
- break;
- }
- else
- {
- topToken=operStack.top( );
- operStack.pop( );
- m_postfix_str.append( BLANK+topToken );
- }
- }
- }
- break;
- default: //operator datas
- {
- m_postfix_str.append( BLANK+token);
- while(1)
- {
- if(isalnum( m_infix_str[ i+1 ] ) || m_infix_str[ i+1 ] =='.' )
- {
- i++;
- token=m_infix_str[ i ];
- m_postfix_str.append(&token);
- }
- else
- break;
- }
- }
- break;
- }//switch
- }//for
- //pop the release operator in the operator stack
- while( 1 )
- {
- if( operStack.empty( ) ) break;
- topToken=operStack.top( );
- operStack.pop( );
- if( topToken !='(' )
- {
- m_postfix_str.append( BLANK+topToken);
- }
- else
- {
- cout<<"ERROR in infix expression/n";
- break;
- }
- }
- m_postfix_str.erase( 0,1 ); //delete the frist one blank,just for goodlooking
- return m_postfix_str;
- }
- bool infix::strisnum( string str )
- {
- int i;
- int size=str.length( );
- for( i=0;i<size;++i )
- {
- if( isalnum( str[ i ] ) || str[ i ] =='.');
- else
- return 0;
- }
- if( i==size )
- return 1;
- }
- bool infix::strisoper(string tempstr)
- {
- if(*tempstr.c_str( )=='+'||*tempstr.c_str( )=='-'||
- *tempstr.c_str( )=='*'||*tempstr.c_str( )=='/' ||*tempstr.c_str( )=='%')
- return 1;
- else
- return 0;
- }
- float infix::value( )
- {
- stack<float> numstack; //store the number and the middle result
- istringstream isstream( m_postfix_str,istringstream::in);
- string tempstr;
- float num_one,num_two;
- while( isstream>>tempstr)
- {
- if( strisnum( tempstr) )
- {
- sscanf( tempstr.c_str( ),"%f", &num_one);
- numstack.push( num_one );
- }
- else if( ( int)numstack.size( ) >1 && strisoper( tempstr ))
- {
- num_one=numstack.top( );
- numstack.pop( );
- num_two=numstack.top( );
- numstack.pop( );
- //WARNING: num_two must be the left opeator data
- switch( *tempstr.c_str( ) ) //const char* string::c_str( )
- {
- case '+':
- numstack.push( num_two+num_one);
- break;
- case '-':
- numstack.push( num_two-num_one);
- break;
- case '*':
- numstack.push( num_two*num_one);
- break;
- case '/':
- numstack.push( num_two/num_one);
- break;
- case '%':
- numstack.push( ( int )num_two% (int)num_one);
- break;
- default:
- std::cerr<<"Unknow operator/n";
- break;
- } //swutch
- }//if-else-if
- }//while
- if((int)numstack.size( )!=1 )
- std::cerr<<"You have input a wrong formula/n";
- return numstack.top( );
- }//infix::value( )
- /*test.cpp*/
- #include "./infix.h"
- #include <iostream>
- #include <string>
- using std::cout;
- using std::cin;
- using std::endl;
- using std::string;
- int main( )
- {
- cout<<"******Attention: -x please change to ( 0-x ) !******/n";
- string str( "((0-1)+2)*3/4+3*( 238.123-46 )" ); //the result is 577.119
- infix one( str);
- string poststr=one.get_postfix( );
- cout<<poststr<<endl;
- cout<< one.value( )<<endl;
- string strstr( "((0-1)+2)*3/4+3*( (0-0.5)-1 )" ); //the result is -3.75
- infix two( strstr);
- string ststr=two.get_postfix( );
- cout<<ststr<<endl;
- cout<< two.value( )<<endl;
- return 0;
- }
- 定义一个中缀式类,可以求其后缀式以及计算其值
- 中缀表达式转为后缀表达式以及后缀表达式的计算
- 中缀表达式变为后缀表达式,以及后缀表达式的计算
- 计算公式中缀式与后缀式的转换
- "括号匹配, 中缀表达式转化为后缀表示式, 计算中缀表达式, 计算后缀表达式"完整代码
- 中缀表达式改后缀并计算值
- 中缀表达式转后缀并计算值
- 【转】算术表达式中缀形式转后缀形式,并基于后缀式和栈进行计算
- 栈的应用(括号匹配、后缀表式计算、中缀转后缀)
- 中缀式构造后缀式
- 后缀式中中缀式
- 中缀式变后缀式
- 中缀式转后缀式
- 中缀式变后缀式
- 中缀式变后缀式
- 中缀式变后缀式
- 中缀式变后缀式
- 中缀式变为后缀式
- 从编译wxWidget到在VC6中创建工程项目步骤
- javascript 比较开始时间和结束时间
- wp7学习笔记1——Silverlight初体验
- windows下LIBSVM使用方法及例子
- C++ 开发入门之---项目文件说明
- 定义一个中缀式类,可以求其后缀式以及计算其值
- 【转载】JavaScript: 使用面向对象的技术创建高级 Web 应用程序
- 内存对齐
- 获取积分
- 关于外连接
- sqlserver 查看表结构 字段 长度的2种方式
- The Java HotSpotTM Server VM
- 回归
- Java优化策略(一):底层优化