Monads/Writer monad: Difference between revisions

Content added Content deleted
(→‎{{header|JavaScript}}: (added comments at two stages))
Line 17: Line 17:
<lang JavaScript>(function () {
<lang JavaScript>(function () {
'use strict';
'use strict';

// START WITH THREE SIMPLE FUNCTIONS
// START WITH THREE SIMPLE FUNCTIONS

// Square root of a number more than 0
// Square root of a number more than 0
function root(x) {
function root(x) {
return Math.sqrt(x);
return Math.sqrt(x);
}
}

// Add 1
// Add 1
function addOne(x) {
function addOne(x) {
return x + 1;
return x + 1;
}
}

// Divide by 2
// Divide by 2
function half(x) {
function half(x) {
return x / 2;
return x / 2;
}
}


// DERIVE LOGGING VERSIONS OF EACH FUNCTION
// DERIVE LOGGING VERSIONS OF EACH FUNCTION

function loggingVersion(f, strLog) {
function loggingVersion(f, strLog) {
return function (v) {
return function (v) {
Line 46: Line 46:
}
}
}
}

var log_root = loggingVersion(root, "obtained square root"),
var log_root = loggingVersion(root, "obtained square root"),

log_addOne = loggingVersion(addOne, "added 1"),
log_addOne = loggingVersion(addOne, "added 1"),

log_half = loggingVersion(half, "divided by 2");
log_half = loggingVersion(half, "divided by 2");



// UNIT/RETURN and BIND for the the WRITER MONAD
// UNIT/RETURN and BIND for the the WRITER MONAD

// The Unit / Return function for the Writer monad:
// The Unit / Return function for the Writer monad:
// 'Lifts' a raw value into the wrapped form
// 'Lifts' a raw value into the wrapped form
Line 66: Line 66:
};
};
}
}

// The Bind function for the Writer monad:
// The Bind function for the Writer monad:
// applies a logging version of a function
// applies a logging version of a function
// to the contents of a wrapped value
// to the contents of a wrapped value
// and return a wrapped result (with extended log)
// and return a wrapped result (with extended log)

// Writer a -> (a -> Writer b) -> Writer b
// Writer a -> (a -> Writer b) -> Writer b
function writerBind(w, f) {
function writerBind(w, f) {
var writerB = f(w.value);
var writerB = f(w.value);

return {
return {
value: writerB.value,
value: writerB.value,
Line 81: Line 81:
};
};
}
}

// USING UNIT AND BIND TO COMPOSE LOGGING FUNCTIONS
// USING UNIT AND BIND TO COMPOSE LOGGING FUNCTIONS

// We can compose a chain of Writer functions (of any length) with a simple foldr/reduceRight
// We can compose a chain of Writer functions (of any length) with a simple foldr/reduceRight
// which starts by 'lifting' the initial value into a Writer wrapping,
// which starts by 'lifting' the initial value into a Writer wrapping,
Line 93: Line 93:
}, writerUnit(value));
}, writerUnit(value));
}
}

var half_of_addOne_of_root = function (v) {
var half_of_addOne_of_root = function (v) {
return logCompose(
return logCompose(
Line 99: Line 99:
);
);
};
};

return half_of_addOne_of_root(5);
return half_of_addOne_of_root(5);
})();</lang>
})();</lang>