Skip to content

Instantly share code, notes, and snippets.

@FormallyMyles
Last active May 13, 2016 23:33
Show Gist options
  • Save FormallyMyles/267a72c90f4f173df4f9aa4489b3f4bd to your computer and use it in GitHub Desktop.
Save FormallyMyles/267a72c90f4f173df4f9aa4489b3f4bd to your computer and use it in GitHub Desktop.
Very Simple Javascript Expression Evaluator
function evaluate(input) {
// Supported ops (brackets arent really there)
var ops = ["(", ")", "^", "/", "*", "%", "+", "-"];
// Check brackets
var j = 0;
for (var i = 0; i < input.length; i++) {
if (input.charAt(i) == "(")
j++;
if (input.charAt(i) == ")")
j--;
}
if (j != 0) {
throw "Bracket Mismatch!";
}
// Iterate through terms
var node = function(val) {
return {
element: val,
left: undefined,
right: undefined
};
};
var opStack = []; // top of stack is .length - 1
var valStack = []; // top of stack is .length - 1
function push() {
// each op has 2 parameters
var n = opStack.pop();
if (valStack.length < 2)
throw "Lonely operators! Invalid expression!";
n.right = valStack.pop(); // every op has 2 params
n.left = valStack.pop();
valStack.push(n); // push back onto value stack
}
for (var i = 0; i < input.length; i++) {
var current = input.charAt(i);
if (current == "(") {
// Open
opStack.push(node(current));
continue;
}
if (current == ")") {
// Close
while (opStack[opStack.length - 1].element != "(") {
push();
}
opStack.pop(); // remove the other bracket "("
continue;
}
if (ops.indexOf(current) != -1) {
// Op
while (opStack.length > 0 && opStack[opStack.length - 1].element != "(" && ops.indexOf(current) >= ops.indexOf(opStack[opStack.length - 1])) {
push();
}
opStack.push(node(current));
} else {
if (current != " ") {
// Handle this number as anything till next op.
for (var x = i + 1; x < input.length; x++) {
if (ops.indexOf(input.charAt(x)) == -1) {
i++;
current = current + input.charAt(x);
} else {
break;
}
}
// Number
valStack.push(node(current));
}
}
}
// make remaining
while (opStack.length > 0) {
push();
}
// print
function traverse(node) {
if (ops.indexOf(node.element) != -1 && node.left != undefined && node.right != undefined) {
var x = traverse(node.left);
var y = traverse(node.right);
var i = ops.indexOf(node.element);
if (i == 2)
return x ^ y;
if (i == 3)
return x / y;
if (i == 4)
return x * y;
if (i == 5)
return x % y;
if (i == 6)
return x + y;
if (i == 7)
return x - y;
return 0;
} else {
return parseInt(node.element);
}
}
return traverse(valStack[valStack.length - 1]);
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment