Expression evaluator
- utopiomania
- Addict
- Posts: 1655
- Joined: Tue May 10, 2005 10:00 pm
- Location: Norway
-
- Enthusiast
- Posts: 130
- Joined: Thu Oct 20, 2011 7:22 am
Re: Expression evaluator
Hi, tried this expression evaluator in a real time sound synthesis app - it evaluated accurately but proved too expensive for each sample calculation for the audio streaming. Would there be any interest in someone having a crack at a PB interface for muparser for example?
http://beltoforion.de/article.php?a=muparser
It says:
http://beltoforion.de/article.php?a=muparser
It says:
Many applications require the parsing of mathematical expressions. The main objective of this library is to provide a fast and easy way of doing this. Written in C++, it works by transforming a mathematical expression into bytecode and precalculating constant parts of the expression. All languages that are able to use DLLs that export plain C functions should be able to use this parser. Due to the wrapper being necessary, there is some overhead associated with using the dynamic library. The following files are required: muParserDLL.h, muParser.lib, muParser.dll. Include the header file in your project and add the lib file to the project resources
Re: Expression evaluator
Code: Select all
ImportC "muparser32.lib"
mupCreate (nBaseType.l) ;As "mupCreate"
mupRelease (*a_hParser) ;As "mupRelease"
mupSetExpr (*a_hParser, a_szExpr.s) ;As "mupSetExpr"
mupDefinePostfixOprt (*a_hParser, a_szName.s, *a_pOprt, a_bOptimize.l) ;As "mupDefinePostfixOprt"
mupDefineVar (*a_hParser, a_szName.s, *a_fVar) ;As "mupDefineVar"
mupEval.d (*a_hParser) ;As "mupEval"
mupSetVarFactory (*a_hParser, *a_pFactory, *pUserData) ;As "mupSetVarFactory"
mupSetErrorHandler (*a_hParser, *a_pErrHandler) ;As "mupSetErrorHandler"
mupGetErrorMsg (*a_hParser) ;As "mupGetErrorMsg" ;const muChar_t ptr
mupGetErrorToken (*a_hParsert) ;As "mupGetErrorToken" ;const muChar_t ptr
mupGetErrorPos (*a_hParser) ;As "mupGetErrorPos" ;muInt_t
mupGetErrorCode (*a_hParser) ;As "mupGetErrorCode" ;muInt_t
EndImport
#PARSER_MAXVARS = 10
ProcedureC.d Factorial (x.d)
Define.l i, n
f.d
f = 1
n = x
If n > 0
For i = 1 To n
f = f * i
Next
EndIf
ProcedureReturn f
EndProcedure
;---------------------------------------------------------------------------
;Factory function For creating new parser variables
; This could As well be a function performing database queries.
ProcedureC AddVariable(a_szName.s, *pUserData)
Static Dim afValBuf.d(#PARSER_MAXVARS) ; I don't want dynamic allocation here
Static iVal.i = 0 ; so i used this buffer
PrintN("Generating new variable "+a_szName+" (slots left: "+Str(#PARSER_MAXVARS-iVal)+")")
;;;Debug("Generating new variable "+a_szName+" (slots left: "+Str(#PARSER_MAXVARS-iVal)+")")
;MessageBox_(0, "Generating new variable "+a_szName+" (slots left: "+Str(#PARSER_MAXVARS-iVal)+")", "AddVariable",0)
afValBuf(iVal) = 0
If (iVal>=#PARSER_MAXVARS-1)
Debug("Variable buffer overflow.")
;MessageBox_(0, "Variable buffer overflow.", "AddVariable",0)
ProcedureReturn 0
EndIf
iVal=iVal+1
ProcedureReturn @afValBuf(iVal-1)
EndProcedure
ProcedureC OnError (*hParser)
PrintN("")
PrintN("Error:")
PrintN("------")
PrintN("Message: "+Chr(34)+PeekS(mupGetErrorMsg(*hParser),-1,#PB_Ascii)+Chr(34))
PrintN("Token: "+Chr(34)+PeekS(mupGetErrorToken(*hParser),-1,#PB_Ascii)+Chr(34))
PrintN("Position: "+Str(mupGetErrorPos(*hParser)))
PrintN("Errc: "+Str(mupGetErrorCode(*hParser)))
ProcedureReturn 0
EndProcedure
;---------------------------------------------------------------------------
OpenConsole()
x.d
y.d
EvalResult.d
Equation.s
ts.s
hParser.i
x = 3
hParser=mupCreate(0)
PrintN("hParse = "+Str(hParse))
mupSetVarFactory(hParser, @AddVariable(), 0)
mupDefineVar (hParser, "x", @x) ;map variable X to "x"
mupDefineVar (hParser, "y", @y) ;map variable Y To "y"
mupSetErrorHandler(hParser, @OnError())
;CompilerIf 1
mupDefinePostfixOprt(hParser,"!", @Factorial(),0)
Equation = "z=x!"
mupSetExpr (hParser, Equation)
X = 7
EvalResult = mupEval(hParser) ;evaluate expression
PrintN("z="+StrD(X)+"! = "+StrD(EvalResult))
Equation = "z=z*8"
mupSetExpr (hParser, Equation)
EvalResult = mupEval(hParser) ;evaluate expression
PrintN("z=z*8 = "+StrD(EvalResult)) ;EvalResult
;CompilerEndIf
Equation = "y=x*x"
mupSetExpr (hParser, Equation)
EvalResult = mupEval(hParser) ;evaluate expression
PrintN(StrD(x)+"*"+StrD(x)+" = "+StrD(y)) ;EvalResult
mupRelease(hParser)
Print("Press return to exit ")
Input()
CloseConsole()
Last edited by jack on Thu Mar 23, 2017 3:03 am, edited 1 time in total.
-
- Enthusiast
- Posts: 130
- Joined: Thu Oct 20, 2011 7:22 am
Re: Expression evaluator
thanks, but am getting this:
Error:
------
Message: ""
Token: ""
Position: -1
Errc: 21
Error:
------
Message: ""
Token: ""
Position: 0
Errc: 1
z=7! = 0
Error:
------
Message: ""
Token: ""
Position: 0
Errc: 1
z=z*8 = 0
Error:
------
Message: ""
Token: ""
Position: 0
Errc: 1
7*7 = 0
Press return to exit
am making reference to the lib from here:
https://github.com/beltoforion/muparser ... s/example2
Error:
------
Message: ""
Token: ""
Position: -1
Errc: 21
Error:
------
Message: ""
Token: ""
Position: 0
Errc: 1
z=7! = 0
Error:
------
Message: ""
Token: ""
Position: 0
Errc: 1
z=z*8 = 0
Error:
------
Message: ""
Token: ""
Position: 0
Errc: 1
7*7 = 0
Press return to exit
am making reference to the lib from here:
https://github.com/beltoforion/muparser ... s/example2
Re: Expression evaluator
do you have visual studio installed?
you can build the libraries yourself there's a VS solution in the build directory
you can build the libraries yourself there's a VS solution in the build directory
Re: Expression evaluator
try again, I updated the code.
-
- Enthusiast
- Posts: 130
- Joined: Thu Oct 20, 2011 7:22 am
Re: Expression evaluator
No I don't have VS installed, but thanks very much for the code update, as it seems to have done the trick
Result:
hParse = 0
Generating new variable z (slots left: 10)
z=7! = 5040
z=z*8 = 40320
7*7 = 49
Press return to exit
Result:
hParse = 0
Generating new variable z (slots left: 10)
z=7! = 5040
z=z*8 = 40320
7*7 = 49
Press return to exit
Re: Expression evaluator
Any chance someone has a compiled muparser.dll compiled for windows? I'm on a metered connection & don't want to download vss.
Re: Expression evaluator
you can get the dll from https://github.com/beltoforion/muparser ... s/example2
Re: Expression evaluator
Thank you - I did not see that. (Any idea why 64bit doesn't work?)
Re: Expression evaluator
I have been trying to figure that out, it works on 64-bit if in the imports you change the string type to p-AsciiDamion12 wrote:(Any idea why 64bit doesn't work?)
but then it won't work on 32-bit, perhaps somebody can spot what the problem is.
Code: Select all
CompilerIf #PB_Compiler_OS = #PB_OS_Windows And #PB_Compiler_Processor = #PB_Processor_x64
ImportC "muparser64.lib"
CompilerElseIf #PB_Compiler_OS = #PB_OS_Windows And #PB_Compiler_Processor = #PB_Processor_x86
ImportC "muparser32.lib"
CompilerEndIf
mupCreate (nBaseType.l) ;As "mupCreate"
mupRelease (*a_hParser) ;As "mupRelease"
mupSetExpr (*a_hParser, a_szExpr.p-Ascii) ;As "mupSetExpr"
mupDefinePostfixOprt (*a_hParser, a_szName.p-Ascii, *a_pOprt, a_bOptimize.l) ;As "mupDefinePostfixOprt"
mupDefineVar (*a_hParser, a_szName.p-Ascii, *a_fVar) ;As "mupDefineVar"
mupEval.d (*a_hParser) ;As "mupEval"
mupSetVarFactory (*a_hParser, *a_pFactory, *pUserData) ;As "mupSetVarFactory"
mupSetErrorHandler (*a_hParser, *a_pErrHandler) ;As "mupSetErrorHandler"
mupGetErrorMsg (*a_hParser) ;As "mupGetErrorMsg" ;const muChar_t ptr
mupGetErrorToken (*a_hParsert) ;As "mupGetErrorToken" ;const muChar_t ptr
mupGetErrorPos (*a_hParser) ;As "mupGetErrorPos" ;muInt_t
mupGetErrorCode (*a_hParser) ;As "mupGetErrorCode" ;muInt_t
EndImport