Skip to content

Instantly share code, notes, and snippets.

@aneurysmjs
Created April 15, 2019 21:42
Show Gist options
  • Save aneurysmjs/d5aab43b07ace10b7f15fee5ea43a963 to your computer and use it in GitHub Desktop.
Save aneurysmjs/d5aab43b07ace10b7f15fee5ea43a963 to your computer and use it in GitHub Desktop.
monad axioms
// Axioms
bind(init(value), f) === f(value)
bind(monad, unit) === monad
bind(bind(monad, f), g) ===
bind(monad, function (value) {
return bind(f(value), g);
});
// the OO transform
bind(monad, fn)
monad.bind(fn)
// macroid (acts like a macro)
function MONAD() {
// make and object that inherits nothing - создать объект который ничего наследует
let prototype = Object.create(null);
function unit(value) {
// anything that goes into the prototype object will be inherited by the monads we make
let monad = Object.create(prototype);
monad.bind = function (fn, args) {
return fn(value, ...args);
};
return monad;
};
// allow us to add additional properties to the prototype
unit.method = function method(name, fn) {
prototype[name] = fn;
// it also returns unit so we can then call .method().method().method()
return unit;
};
// takes an ordinary function and add it to the prototype
unit.lift = function lift(name, fn) {
// but it'll wrap that function into another function, which will
// call `unit` and `bind` as suggested in the first 2 axioms, so it
// allows that function to act as thought it knew about monads, even
// thought it didn't
prototype[name] = function (...args) {
// call `bind` for us and the it'll then wrap it's result in a monad
// if it needs to
return unit(this.bind(fn, args));
};
return unit;
};
return unit;
}
// identify monad
const identity = MONAD();
const monad = identity('Джеро');
monad.bind(console.log); // Джеро
// lift
const get = MONAD().lift('log', console.log);
const myMonad = get('some text');
myMonad.log();
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment