Created
January 26, 2012 03:32
-
-
Save fogus/1680795 to your computer and use it in GitHub Desktop.
*psil, pocket lisp interpreter
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
var cx = new env; | |
console.log(leval(['set','a',42],cx)); | |
console.log(leval('a',cx)); | |
console.log(leval(['eq',42,'a'],cx)); | |
console.log(leval(['quote',[1,2]],cx)); | |
console.log(leval(['fst',['quote',[1,2]]],cx)); | |
console.log(leval(['rst',['quote',[1,2]]],cx)); | |
console.log(leval(['cons',1,['quote',[2,3]]],cx)); | |
console.log(leval(['cond',['eq',1,2],42,43],cx)); | |
console.log(leval(['atom',['quote',[1,2]]],cx)); | |
console.log(leval(['set','second',['quote',['lambda',['x'],['fst',['rst','x']]]]],cx)); | |
console.log(leval(['second',['quote',[1,2,3]]],cx)); |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
function extcx(ar,cx){ | |
return ar.reduce(function(o, kv){ o[kv[0]] = kv[1]; return o; },cx || {}) | |
} | |
function zip(ar1, ar2){ | |
return ar1.reduce(function(ar, v1, i1){ if (ar2[i1]) ar.push([v1,ar2[i1]]); return ar; },[]) | |
} | |
function atomp(a){ return !(typeof a in {object:0,array:0}) } | |
function lazyp(a){ return (a in {cond:0,quote:0,lambda:0}) } | |
function env(){ | |
var inst = this; | |
inst.atom = function(a){ return atomp(a) }; | |
inst.set = function(as){ return inst[as[0]] = as[1] }; | |
inst.quote = function(as){ return as[0] }; | |
inst.fst = function(as){ return as[0][0] }; | |
inst.rst = function(as){ return as[0].slice(1) }; | |
inst.cons = function(as){ return [as[0]].concat(as[1]) }; | |
inst.eq = function(as){ return as[0] === as[1] }; | |
inst.cond = function(as,cx){ return leval(as[0],cx) ? leval(as[1],cx) : leval(as[2],cx) }; | |
return inst; | |
} | |
function apply(rf, as, cx){ | |
return rf in cx && cx[rf].call ? cx[rf].call(null, as, cx) : leval(cx[rf][2], extcx(zip(cx[rf][1], as), cx)); | |
} | |
function leval(sx, cx){ | |
if (atomp(sx)) return sx in cx ? cx[sx] : sx; | |
var rf = sx[0], as = sx.slice(1).map(function(a){ return lazyp(rf) ? a : leval(a, cx) }); | |
return apply(rf, as, cx); | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment