Skip to content

Instantly share code, notes, and snippets.

@uiur
Created February 7, 2013 05:02
Show Gist options
  • Save uiur/4728686 to your computer and use it in GitHub Desktop.
Save uiur/4728686 to your computer and use it in GitHub Desktop.
function Parser() {
var that = {}
, at
, current
, tokens;
function tokenize(source) {
return source.replace(/\(/g, ' ( ').replace(/\)/g, ' ) ').split(/\s/).filter(function(t){ return t !== ""; });
}
function expression() {
var value;
if (current === '(') {
value = [];
next();
while (current !== ')') {
value.push(expression());
}
next();
} else if (isNumber(current)){
value = number();
} else if (isBool(current)) {
value = bool();
} else {
value = current;
next();
}
return value;
}
function isNumber(token) {
return !isNaN(+token);
}
function number() {
var value = +current;
next();
return value;
}
function isBool(token) {
return token === '#t' || token === '#f';
}
function bool() {
var value;
if (current === '#t') value = true;
if (current === '#f') value = false;
if (value === undefined) throw new Error();
next();
return value;
}
function next() {
current = tokens[at];
at += 1;
return current;
}
that.read = function (source) {
at = 0;
current = "";
tokens = tokenize(source);
next();
return expression();
};
return that;
}
/*
var p = new Parser();
console.log(p.read('192338'));
console.log(p.read('(def a b)'));
console.log(p.read('(def a (lambda (a) (+ 1 2)))'));
console.log(p.read('(if #t (+ 1 (* 2 3 4 5)))'));
*/
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment