parsing - How do you write an arithmetic expression parser in JavaScript, without using eval or a constructor function? -
given string:
var str1 = "25*5+5*7";
without using eval
or constructor function in javascript, how able write function called "output" takes in string , outputs arithmetic value of string, in case 160?
here's full precedence expression evaluator following recursive parsing idea linked-to in comment on op's question.
to this, first wrote simple bnf grammar expressions wanted process:
sum = product | sum "+" product | sum "-" product ; product = term | product "*" term | product "/" term ; term = "-" term | "(" sum ")" | number ;
this requires bit of experience , straightforwardly. if have no experience bnf find incredibly useful describing complex streams of items expressions, messages, programming langauges, ...
using grammar, followed procedure outlined in other message produce following code. should obvious driven grammar in dumb mechanical way, , therefore pretty easy write if have grammar.
(untested. i'm not javascript coder. surely contain few syntax/semantic hiccups. took me @ 15 minutes code.)
var se="syntax error"; function parse(str) { // returns integer expression result or se var text=str; var scan=1; return parse_sum(); function parse_sum() { var number, number2; if (number=parse_product()==se) return se; while (true) { skip_blanks(); if (match("+") { number2=parse_product(); if (number2==se) return se; number+=number2; } else if (match('-')) { { number2=parse_product(); if (number2==se) return se; number-=number2; } else return number; } } function parse_product() { var number, number2; if (number=parse_number()==se) return se; while (true) { if (match("*") { number2=parse_term(); if (number2==se) return se; number*=number2; } else if (match('/')) { number2=parse_term(); if (number2==se) return se; number/=number2; } else return number; } } function parse_term() { var number; skip_blanks(); if (match("(")) { number=parse_sum(); if (number=se) return se; skip_blanks(); if (!match(")") return se; } else if match("-") { number= - parse_term(); } else if (number=parse_number()==se) return se; return number; } function skip_blanks() { while (match(" ")) { }; return; } function parse_number() { number=0; if (is_digit()) { while (is_digit()) {} return number; } else return se; } var number; function is_digit() { // following 2 lines wrong in detail not intent if (text[scan]>="0" && text[scan]<="9") { number=number*10+text[scan].toint(); return true; } else return false; } function match(c) { if (text[scan]==c) { scan++; return true } else return false; } }
it straightforward code such parsers/evaluators. see my answer on how build parser (which links how how build evaluator).
Comments
Post a Comment