Does anyone have any idea about how to make MATLAB take in a string suppose
f(x) = 3*x + 5*(2+100) ,where x = 5
But disregard all rules of precedence (including parenthesis) and solely calculate from left to right. So the answer to above would be 140 instead of 525
I was thinking that it would be along the lines of
[s,r] = strtok(myString,'0123456789');
put in a for loop but i haven't been able to figure out exactly how to do it.
Please Help! Thank You
Well, for a simple expression, one way to do it is to:
Of course in your case we also first have to handle the case of the "function expression". It means detecting the "variable" (x
in your case), and retrieving it value. So the code proposed get quite longer just because of that.
It works fine on your example, and should be ok for different expressions as long as they respect the same style. In any case it will only works for function of one variable.
You may have to add a few of the characters to ignore. Only parenthesis (
and )
are ignored at the moment, but you could add brackets []
and any other symbols that your expression may include and you want to ignore. (add that in the "Tidy up" paragraph.)
%% // starting point
myStr = 'f(x) = 3*x + 5*(2+100) ,where x = 5' ;
%% // find "input variables" in the header
strVar = regexp(myStr, '\(([^\)]+)\)' , 'tokens' , 'once' ) ;
strVar = char(strVar) ; %// => strVar='x'
%% // isolate only the function expression (without the header or the x assignation )
ibeg = strfind( myStr , '=' )+1 ; %// ibeg= 7 find the last position of the expression
iend = strfind( myStr , ',' )-1 ; %// iend= 23 find the last position of the expression
fstr = myStr(ibeg(1):iend(1)) ; %// now fstr='3*x+5*(2+100)' separate only function expression
%% // get the value of the variable at the end of the expression
var = regexp( myStr(iend:end) , [ strVar '\s*=\s*(\d+)'] , 'tokens' ) ;
%// then replace it in the function expression
fstr = regexprep(fstr, ['(' strVar ')' ] , var{1} ) ; %// Now you function looks like this: "3*5 + 5*(2+100)"
%% // THIS IS THE INTERESTING BIT
%// everything before was only to extract the specific expression
%% // now tidy up
fstr(isspace(fstr)) = [] ; %// remove white space characters
idx2remove = [ strfind(fstr,'(') strfind(fstr,')') ]; %// get indices of characters to ignore/remove
fstr( idx2remove ) = [] ; %// Now you function looks like this: "3*5+5*2+100"
%% // get the digits and the operators separately
digits = regexp( fstr , '(\d+)' , 'tokens' ) ; %// extract the numbers
oper = regexp( fstr , '(\d+)' , 'split' ) ; %// extract the operators
oper = oper(2:end) ; %// remove first empty cell
%% // now rebuild the expression with pure left to right precedence
strFinalFunction = [ '(' char(digits{1}) , char(oper{1}) , char(digits{2}) ')' ] ;
for op = 3:length(digits)
strFinalFunction = ['(' strFinalFunction char(oper{op-1}) char(digits{op}) ')'] ;
end
%// now your function look like: "((((3*5)+5)*2)+100)"
result = eval( strFinalFunction ) %// then evaluate
note: It will not work if your expression contains function (like cos
or sqrt
etc...). The power operator ^
will work though, and its precedence will also be overridden.