Skip to content

Instantly share code, notes, and snippets.

@timruffles
Created June 7, 2016 09:30
Show Gist options
  • Star 2 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save timruffles/d58e535e66e4041dd0173f782ce39db6 to your computer and use it in GitHub Desktop.
Save timruffles/d58e535e66e4041dd0173f782ce39db6 to your computer and use it in GitHub Desktop.
functor in TypeScript - this is probably in violation of many functor laws :/
interface Functor<T> {
map(mapper: (x: T) => T): Functor<T>;
ret(x: T): Functor<T>;
}
class Maybe<T> implements Functor<T> {
constructor(private value: T) {}
private nowt() {
return this.value == null;
}
map(f: (x: T) => T): Functor<T> {
return this.nowt() ? this : new Maybe<T>(f(this.value));
}
ret(x: T) {
return new Maybe<T>;
}
}
class ListF<T> implements Functor<T> {
constructor(private values: T[]) {}
map(f: (x: T) => T): Functor<T> {
return new ListF<T>(this.values.map(f));
}
ret(x: T) {
return new ListF([x]);
}
}
type promiseResolution<T> = Error | T;
class PromiseF<T> implements Functor<T> {
private promise: Promise<T>;
constructor(value: promiseResolution<T>) {
this.promise = this.valueToPromise(value);
}
map(f: (x: T) => T): Functor<T> {
return new PromiseF(this.promise.then(f))
}
ret(x: T) {
return new PromiseF(this.valueToPromise(x));
}
private valueToPromise(x: promiseResolution<T>) {
return x instanceof Error
? Promise.reject(x)
: Promise.resolve(x)
}
}
new Maybe<number>(null)
.map((x) => x + 1)
.map(tap(x=>console.log(x)))
new Maybe<number>(10)
.map((x) => x + 1)
.map(tap(x=>console.log(x)))
function tap(f) {
return (x) => { f(x); return x }
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment