Skip to content

Instantly share code, notes, and snippets.

@thomasvrgn
Created March 6, 2021 09:48
Show Gist options
  • Select an option

  • Save thomasvrgn/a473274b956e5dcd9402d835825050de to your computer and use it in GitHub Desktop.

Select an option

Save thomasvrgn/a473274b956e5dcd9402d835825050de to your computer and use it in GitHub Desktop.
pour itrooz
const operators = [
{
op: '!',
precedence: 5,
associativity: 'left',
function: (a) => {
let acc = 1;
for (let i = 1; i < a + 1; i++) acc *= i;
return acc;
}
},
{
op: '^',
precedence: 4,
associativity: 'right',
},
{
op: '*',
precedence: 3,
associativity: 'left',
},
{
op: '/',
precedence: 3,
associativity: 'left',
},
{
op: '+',
precedence: 2,
associativity: 'left',
},
{
op: '-',
precedence: 2,
associativity: 'left',
},
{
op: 'sqrt',
precedence: 5,
associativity: 'right',
function: (a) => {
return Math.sqrt(a)
},
}
];
operators.get = function(op) {
return this.find((x) => x.op === op);
}
function tokenize(str) {
return str.split(/\s+/g);
}
function isNumber(el) {
return !isNaN(Number(el));
}
const calculus = '( 5 + 5 ) * 3 + 2 * 5';
const tokens = tokenize(calculus);
function parse(tokens) {
const stack = [];
const queue = [];
for (const token of tokens) {
if (isNumber(token)) {
queue.push(token);
} else if (operators.get(token) !== undefined) {
const op = operators.get(token);
while ((stack.length > 0) &&
((stack[stack.length - 1].precedence > op.precedence)
|| (stack[stack.length - 1].precedence === op.precedence && token.associativity === 'left'))
&& (stack[stack.length - 1].op !== '(')
) {
const popOp = stack.pop();
queue.push(popOp.op);
}
stack.push(op);
} else if (token === '(') {
stack.push({ op: '(' });
} else if (token === ')') {
while (stack[stack.length - 1] && stack[stack.length - 1].op !== '(') {
const popOp = stack.pop();
queue.push(popOp.op);
}
stack.pop();
if (stack[stack.length - 1] && stack[stack.length - 1].function) {
//console.log('FONCTION')
}
}
}
while (stack.length > 0) {
const popOp = stack.pop();
queue.push(popOp.op);
}
return queue;
}
function postfixEvaluator(expr) {
const stack = [];
for (const tok of expr) {
if (isNumber(tok)) {
stack.push(Number(tok))
} else if (operators.get(tok) !== undefined) {
const op = operators.get(tok);
if (op.function) {
const args = [];
while (args.length !== op.function.length) {
args.push(stack.pop());
}
stack.push(op.function(...args));
} else {
const a = stack.pop();
const b = stack.pop();
stack.push(eval(`${b} ${tok} ${a}`));
}
}
}
return stack[0];
}
const postfix = parse(tokens);
console.log(postfixEvaluator(postfix))
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment