Skip to content

Instantly share code, notes, and snippets.

@yuanchuan
Last active October 28, 2017 06:28
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 yuanchuan/23f3d52165ba05419ebdbed407ade4a5 to your computer and use it in GitHub Desktop.
Save yuanchuan/23f3d52165ba05419ebdbed407ade4a5 to your computer and use it in GitHub Desktop.
fun
const assert = require('assert');
const cons = (a, list) => _cons => _cons(a, list);
const car = list => list(head => head);
const cdr = list => list((_, tail) => tail);
const nil = () => null;
const is_nil = list => car(list) === nil();
const length = list =>
is_nil(list) ? 0 : 1 + length(cdr(list));
const nth = (list, n) =>
(n == 0) ? car(list) : nth(cdr(list), n - 1);
const foldl = (f, list, acc) =>
is_nil(list) ? acc : foldl(f, cdr(list), f(acc, car(list)));
const foldr = (f, list, acc) =>
is_nil(list) ? acc : f(foldr(f, cdr(list), acc), car(list));
const reverse = list =>
foldl((acc, x) => cons(x, acc), list, nil);
const map = (f, list) =>
foldr((acc, x) => cons(f(x), acc), list, nil);
const filter = (f, list) =>
is_nil(list) ? nil : (
f(car(list))
? cons(car(list), filter(f, cdr(list)))
: filter(f, cdr(list)));
const L = cons(1, cons(2, cons(3, cons(4, cons(5, nil)))));
assert( length(L) === 5 );
assert( nth(L, 3) === 4 );
assert( car(L) === 1 );
assert( car(cdr(L)) === 2 );
assert( car(map(a => a * 2, L)) === 2 );
assert( car(filter(a => a > 3, L)) === 4 );
assert( car(reverse(L)) === 5 );
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment