Skip to content

Instantly share code, notes, and snippets.

@L8D
Created September 13, 2014 06:52
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save L8D/ee8cc3b11ce78b795bb7 to your computer and use it in GitHub Desktop.
Save L8D/ee8cc3b11ce78b795bb7 to your computer and use it in GitHub Desktop.
RL Interpreter in JavaScript...Because FUN
(function(root, factory) {
if (typeof define === 'function') {
define(factory);
} else if (typeof exports === 'object') {
module.exports = factory();
} else {
root.RL = factory();
}
})(this, function() {
var run = function(code, stack, dict) {
var word, words, stack = stack || [], dict = dict || {};
if (code instanceof Array) {
words = code;
} else {
var words = code.split(/\s+/g).map(function(word, n) {
if (isNaN(n = parseFloat(word))) {
return word.toLowerCase();
} else {
return n;
}
}).reverse();
}
while (words.length) {
word = words.pop();
if (typeof word === 'number') {
stack.push(word);
} else {
var entry;
if (library[word]) {
entry = library[word];
} else if (dict[word]) {
entry = dict[word];
} else {
entry = null;
}
if (typeof entry === 'function') {
entry(stack, words, dict);
} else {
stack.push(entry);
}
}
}
return stack;
};
var library = {
':': function(stack, words, dict) {
var word, block = [];
while ((word = words.pop()) !== ';') {
block.push(word);
}
dict[block.shift()] = function(stack, words, dict) {
run(block.slice(0), stack, dict);
};
},
dup: function(stack) {
var x = stack.pop();
stack.push(x);
stack.push(x);
},
over: function(stack) {
var first = stack.pop(), second = stack.pop();
stack.push(first);
stack.push(second);
stack.push(first);
},
'2dup': function(stack) {
var first = stack.pop(), second = stack.pop();
stack.push(second);
stack.push(first);
stack.push(second);
stack.push(first);
},
rot: function(stack) {
var first = stack.pop(), second = stack.pop(), third = stack.pop();
stack.push(first);
stack.push(third);
stack.push(second);
},
'-rot': function(stack) {
var first = stack.pop(), second = stack.pop(), third = stack.pop();
stack.push(second);
stack.push(first);
stack.push(third);
},
'=': function(stack) {
var y = stack.pop(), x = stack.pop();
stack.push(x === y);
},
'<': function(stack) {
var y = stack.pop(), x = stack.pop();
stack.push(+(x < y));
},
'>': function(stack) {
var y = stack.pop(), x = stack.pop();
stack.push(+(x > y));
},
'<=': function(stack) {
var y = stack.pop(), x = stack.pop();
stack.push(+(x <= y));
},
'>=': function(stack) {
var y = stack.pop(), x = stack.pop();
stack.push(+(x >= y));
},
and: function(stack) {
var y = stack.pop(), x = stack.pop();
stack.push(+(x && y));
},
or: function(stack) {
var y = stack.pop(), x = stack.pop();
stack.push(+(x || y));
},
not: function(stack) {
stack.push(+!stack.pop());
},
min: function(stack) {
var y = stack.pop(), x = stack.pop();
stack.push(Math.min(x, y));
},
max: function(stack) {
var y = stack.pop(), x = stack.pop();
stack.push(Math.max(x, y));
},
'+': function(stack) {
var y = stack.pop(), x = stack.pop();
stack.push(x + y);
},
'-': function(stack) {
var y = stack.pop(), x = stack.pop();
stack.push(x - y);
},
'*': function(stack) {
var y = stack.pop(), x = stack.pop();
stack.push(x * y);
},
'/': function(stack) {
var y = stack.pop(), x = stack.pop();
stack.push(x / y);
},
mod: function(stack) {
var y = stack.pop(), x = stack.pop();
stack.push(x % y);
},
pow: function(stack) {
var y = stack.pop(), x = stack.pop();
stack.push(Math.pow(x, y));
},
atan: function(stack) {
stack.push(Math.atan(stack.pop()));
},
negate: function(stack) {
stack.push(Math.negate(stack.pop()));
},
sin: function(stack) {
stack.push(Math.sin(stack.pop()));
},
cos: function(stack) {
stack.push(Math.cos(stack.pop()));
},
tan: function(stack) {
stack.push(Math.tan(stack.pop()));
},
log: function(stack) {
stack.push(Math.log(stack.pop()));
},
exp: function(stack) {
stack.push(Math.exp(stack.pop()));
},
sqrt: function(stack) {
stack.push(Math.sqrt(stack.pop()));
},
floor: function(stack) {
stack.push(Math.floor(stack.pop()));
},
ceil: function(stack) {
stack.push(Math.ceil(stack.pop()));
},
abs: function(stack) {
stack.push(Math.abs(stack.pop()));
},
pi: Math.PI,
random: function(stack) {
stack.push(Math.random());
}
};
return run;
});
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment