How do I parse and evaluate a mathematical expression in a string (e.g. `'1+1'`

) without invoking `eval(string)`

to yield its numerical value?

With that example, I want the function to accept `'1+1'`

and return `2`

.

How do I parse and evaluate a mathematical expression in a string (e.g. `'1+1'`

) without invoking `eval(string)`

to yield its numerical value?

With that example, I want the function to accept `'1+1'`

and return `2`

.

javascript
string
math
numbers
137
0
wheresrhys
2020-03-17 12:31:28 +0000 UTC

You can use the JavaScript Expression Evaluator library, which allows you to do stuff like:

```
Parser.evaluate("2 ^ x", { x: 3 });
```

Or mathjs, which allows stuff like:

```
math.eval('sin(45 deg) ^ 2');
```

I ended up choosing mathjs for one of my projects.

// You can do + or - easily:

```
function addbits(s){
var total= 0, s= s.match(/[+\-]*(\.\d+|\d+(\.\d+)?)/g) || [];
while(s.length){
total+= parseFloat(s.shift());
}
return total;
}
var string='1+23+4+5-30';
addbits(string)
```

More complicated math makes eval more attractive- and certainly simpler to write.

Somebody has to parse that string. If it's not the interpreter (via `eval`

) then it'll need to be you, writing a parsing routine to extract numbers, operators, and anything else you want to support in a mathematical expression.

So, no, there isn't any (simple) way without `eval`

. If you're concerned about security (because the input you're parsing isn't from a source you control), maybe you can check the input's format (via a whitelist regex filter) before passing it to `eval`

?

An alternative to the excellent answer by @kennebec, using a shorter regular expression and allowing spaces between operators

```
function addbits(s) {
var total = 0;
s = s.replace(/\s/g, '').match(/[+\-]?([0-9\.\s]+)/g) || [];
while(s.length) total += parseFloat(s.shift());
return total;
}
```

Use it like

```
addbits('5 + 30 - 25.1 + 11');
```

**Update**

Here's a more optimised version

```
function addbits(s) {
return (s.replace(/\s/g, '').match(/[+\-]?([0-9\.]+)/g) || [])
.reduce(function(sum, value) {
return parseFloat(sum) + parseFloat(value);
});
}
```

I created BigEval for the same purpose.

In solving expressions, it performs exactly same as `Eval()`

and supports operators like %, ^, &, ** (power) and ! (factorial).
You are also allowed to use functions and constants (or say variables) inside the expression. The expression is solved in PEMDAS order which is common in programming languages including JavaScript.

```
var Obj = new BigEval();
var result = Obj.exec("5! + 6.6e3 * (PI + E)"); // 38795.17158152233
var result2 = Obj.exec("sin(45 * deg)**2 + cos(pi / 4)**2"); // 1
var result3 = Obj.exec("0 & -7 ^ -7 - 0%1 + 6%2"); //-7
```

It can also be made to use those Big Number libraries for arithmetic in case you are dealing with numbers with arbitrary precision.

I went looking for JavaScript libraries for evaluating mathematical expressions, and found these two promising candidates:

JavaScript Expression Evaluator: Smaller and hopefully more light-weight. Allows algebraic expressions, substitutions and a number of functions.

mathjs: Allows complex numbers, matrices and units as well. Built to be used by both in-browser JavaScript and Node.js.

This is a little function I threw together just now to solve this issue - it builds the expression by analyzing the string one character at a time (it's actually pretty quick though). This will take any mathematical expression (limited to +,-,*,/ operators only) and return the result. It can handle negative values and unlimited number operations as well.

The only "to do" left is to make sure it calculates * & / before + & -. Will add that functionality later, but for now this does what I need...

```
/**
* Evaluate a mathematical expression (as a string) and return the result
* @param {String} expr A mathematical expression
* @returns {Decimal} Result of the mathematical expression
* @example
* // Returns -81.4600
* expr("10.04+9.5-1+-100");
*/
function expr (expr) {
var chars = expr.split("");
var n = [], op = [], index = 0, oplast = true;
n[index] = "";
// Parse the expression
for (var c = 0; c < chars.length; c++) {
if (isNaN(parseInt(chars[c])) && chars[c] !== "." && !oplast) {
op[index] = chars[c];
index++;
n[index] = "";
oplast = true;
} else {
n[index] += chars[c];
oplast = false;
}
}
// Calculate the expression
expr = parseFloat(n[0]);
for (var o = 0; o < op.length; o++) {
var num = parseFloat(n[o + 1]);
switch (op[o]) {
case "+":
expr = expr + num;
break;
case "-":
expr = expr - num;
break;
case "*":
expr = expr * num;
break;
case "/":
expr = expr / num;
break;
}
}
return expr;
}
```

I've eventually gone for this solution, which works for summing positive and negative integers (and with a little modification to the regex will work for decimals too):

```
function sum(string) {
return (string.match(/^(-?\d+)(\+-?\d+)*$/)) ? string.split('+').stringSum() : NaN;
}
Array.prototype.stringSum = function() {
var sum = 0;
for(var k=0, kl=this.length;k<kl;k++)
{
sum += +this[k];
}
return sum;
}
```

I'm not sure if it's faster than eval(), but as I have to carry out the operation lots of times I'm far more comfortable runing this script than creating loads of instances of the javascript compiler

Try nerdamer

```
var result = nerdamer('12+2+PI').evaluate();
document.getElementById('text').innerHTML = result.text();
```

```
<script src="http://nerdamer.com/js/nerdamer.core.js"></script>
<div id="text"></div>
```

You can use this well maintained library from **Github** which works on **both Nodejs and Browser** which is faster than other alternative libraries provided here

Usage

```
mexp = require('math-expression-evaluator')
var value = mexp.eval(exp);
```

Try AutoCalculator https://github.com/JavscriptLab/autocalculate Calculate Inputs value and Output By using selector expressions

Just add an attribute for your output input like data-ac="(#firstinput+#secondinput)"

No Need of any initialization just add data-ac attribute only. It will find out dynamically added elements automatically

FOr add 'Rs' with Output just add inside curly bracket data-ac="{Rs}(#firstinput+#secondinput)"

I believe that `parseInt`

and **ES6** can be helpful in this situation

==>in this way:

```
let func = (str) => {
let arr = str.split("");
return `${Number(arr[0]) + parseInt(arr[1] + Number(arr[2]))}`};
console.log(func("1+1"));
```

The main thing here is that `parseInt`

parses the number with the operator. Code can be modified to the corresponding needs.

Here is an algorithmic solution similar to jMichael's that loops through the expression character by character and progressively tracks left/operator/right. The function accumulates the result after each turn it finds an operator character. This version only supports '+' and '-' operators but is written to be extended with other operators. Note: we set 'currOp' to '+' before looping because we assume the expression starts with a positive float. In fact, overall I'm making the assumption that input is similar to what would come from a calculator.

```
function calculate(exp) {
const opMap = {
'+': (a, b) => { return parseFloat(a) + parseFloat(b) },
'-': (a, b) => { return parseFloat(a) - parseFloat(b) },
};
const opList = Object.keys(opMap);
let acc = 0;
let next = '';
let currOp = '+';
for (let char of exp) {
if (opList.includes(char)) {
acc = opMap[currOp](acc, next);
currOp = char;
next = '';
} else {
next += char;
}
}
return currOp === '+' ? acc + parseFloat(next) : acc - parseFloat(next);
}
```

```
const getAddition = (str) => {
return str.split('+').reduce((total, num) => (total + num * 1), 0);
};
const addition = getAddition('1+1');
```

addition is 2.

You could use a for loop to check if the string contains any invalid characters and then use a try...catch with eval to check if the calculation throws an error like `eval("2++")`

would.

```
function evaluateMath(str) {
for (var i = 0; i < str.length; i++) {
if (isNaN(str[i]) && !['+', '-', '/', '*', '%', '**'].includes(str[i])) {
return NaN;
}
}
try {
return eval(str)
} catch (Error) {
return NaN;
}
}
console.log(evaluateMath('2 + 6'))
```

Simple and elegant with `Function()`

```
function parse(str) {
return Function(`'use strict'; return (${str})`)()
}
parse("1+2+3");
```