From f4c20290509d7ed3a8fd5304577e7a4cc0b9d974 Mon Sep 17 00:00:00 2001 From: Mike Buland Date: Tue, 3 Apr 2007 03:49:53 +0000 Subject: Ok, no code is left in src, it's all in src/old. We'll gradually move code back into src as it's fixed and re-org'd. This includes tests, which, I may write a unit test system into libbu++ just to make my life easier. --- src/formula.cpp | 262 -------------------------------------------------------- 1 file changed, 262 deletions(-) delete mode 100644 src/formula.cpp (limited to 'src/formula.cpp') diff --git a/src/formula.cpp b/src/formula.cpp deleted file mode 100644 index cf63cf3..0000000 --- a/src/formula.cpp +++ /dev/null @@ -1,262 +0,0 @@ -#include "formula.h" - -subExceptionDef( ParseException ); - -Formula::Formula() -{ - hVars["pi"] = M_PI; - hVars["e"] = M_E; - - hFunc["sin"] = FuncSin(); -} - -Formula::~Formula() -{ -} - -double Formula::run( char *sFormula ) -{ - for(;;) - { - uint8_t tNum = nextToken( &sFormula ); - if( tNum == symEOS ) - break; - else if( tNum == symSubtract ) - { - tNum = nextToken( &sFormula ); - if( tNum != symNumber ) - throw ParseException("Unary minus must be followed by a number, " - "variable, function, or parenthesis."); - sValue.top() = -sValue.top(); - } - else if( tNum == symOpenParen ) - { - sOper.push( tNum ); - continue; - } - -oppart: uint8_t tOpr = nextToken( &sFormula ); - if( tOpr == symEOS ) - { - //printf("EOS "); - reduce(); - return sValue.top(); - break; - } - if( !sOper.empty() && getPrec( sOper.top() ) > getPrec( tOpr ) ) - { - reduce(); - } - if( tOpr != symCloseParen ) - { - sOper.push( tOpr ); - } - else - { - reduce( true ); - goto oppart; - } - } - return sValue.top(); -} - -void Formula::reduce( bool bCloseParen ) -{ - while( !sOper.empty() ) - { - uint8_t nOpr = sOper.top(); - if( nOpr == symOpenParen ) - { - //printf("Found ( stopping reduction.\n"); - if( bCloseParen == true ) - sOper.pop(); - return; - } - sOper.pop(); - - double dTop = sValue.top(); - sValue.pop(); - - switch( nOpr ) - { - case symAdd: - //printf("%f + %f = %f\n", sValue.top(), dTop, sValue.top()+dTop ); - sValue.top() += dTop; - break; - - case symSubtract: - //printf("%f - %f = %f\n", sValue.top(), dTop, sValue.top()-dTop ); - sValue.top() -= dTop; - break; - - case symMultiply: - //printf("%f * %f = %f\n", sValue.top(), dTop, sValue.top()*dTop ); - sValue.top() *= dTop; - break; - - case symDivide: - //printf("%f / %f = %f\n", sValue.top(), dTop, sValue.top()/dTop ); - sValue.top() /= dTop; - break; - - case symExponent: - //printf("%f ^ %f = %f\n", sValue.top(), dTop, pow(sValue.top(),dTop) ); - sValue.top() = pow( sValue.top(), dTop ); - break; - - case symModulus: - //printf("%f %% %f = %f\n", sValue.top(), dTop, fmod(sValue.top(),dTop) ); - sValue.top() = fmod( sValue.top(), dTop ); - break; - } - } - - if( bCloseParen == true ) - { - throw ParseException("Close-paren found without matching open-paren."); - } -} - -uint8_t Formula::getPrec( uint8_t nOper ) -{ - switch( nOper ) - { - case symNumber: - case symVariable: - case symOpenParen: - case symCloseParen: - return 0; - - case symAdd: - case symSubtract: - return 1; - - case symMultiply: - case symDivide: - case symModulus: - return 2; - - case symExponent: - return 3; - - default: - return 0; - } -} - -uint8_t Formula::nextToken( char **sBuf ) -{ - for(;;) - { - char cbuf = **sBuf; - ++(*sBuf); - switch( cbuf ) - { - case '+': - return symAdd; - - case '-': - return symSubtract; - - case '*': - return symMultiply; - - case '/': - return symDivide; - - case '^': - return symExponent; - - case '%': - return symModulus; - - case '(': - return symOpenParen; - - case ')': - return symCloseParen; - - case ' ': - case '\t': - case '\n': - case '\r': - break; - - case '\0': - return symEOS; - - default: - if( cbuf == '.' || (cbuf >= '0' && cbuf <= '9') ) - { - char num[50]={cbuf}; - int nPos = 1; - bool bDot = false; - - for(;;) - { - cbuf = **sBuf; - if( cbuf == '.' ) - { - if( bDot == false ) - bDot = true; - else - throw ParseException( - "Numbers cannot have more than one " - ". in them." - ); - } - if( cbuf == '.' || (cbuf >= '0' && cbuf <= '9') ) - { - num[nPos++] = cbuf; - } - else - { - num[nPos] = '\0'; - sValue.push( strtod( num, NULL ) ); - return symNumber; - } - ++(*sBuf); - } - } - else if( (cbuf >= 'a' && cbuf <= 'z') || - (cbuf >= 'A' && cbuf <= 'Z') || - (cbuf == '_') ) - { - char tok[50]={cbuf}; - int nPos = 1; - - for(;;) - { - cbuf = **sBuf; - if( (cbuf >= 'a' && cbuf <= 'z') || - (cbuf >= 'A' && cbuf <= 'Z') || - (cbuf >= '0' && cbuf <= '9') || - cbuf == '_' || cbuf == '.' || cbuf == ':' ) - { - tok[nPos++] = cbuf; - } - else - { - tok[nPos] = '\0'; - //printf("Checking variable \"%s\"\n", tok ); - try - { - sValue.push( hVars[tok] ); - return symNumber; - } - catch( HashException &e ) - { - throw ParseException( - "No variable named \"%s\" exists.", - tok - ); - } - } - ++(*sBuf); - } - } - break; - } - } -} - -- cgit v1.2.3