Why The Hipsters Compose Everything

Functional Composition In JavaScript

A. Sharif
A. Sharif
Jul 19, 2015 · 6 min read

Introduction

The Basics

var compose = function(f, g) {
return function(x) {
return f(g(x));
};
};
function reverseAndUpper(str) {
var reversed = reverse(str);
return upperCase(reversed);
}
var reverseAndUpper = compose(upperCase, reverse);
reverseAndUpper('test'); // TSET
function reverseAndUpper(str) {
return upperCase(reverse(str));
}
var compose = function() {
var funcs = Array.protoype.slice.call(arguments);

return funcs.reduce(function(f,g) {
return function() {
return f(g.apply(this, arguments));
};
});
};
Var doSometing = compose(upperCase, reverse, doSomethingInitial); doSomething('foo', 'bar');

Examples

function notEmpty(str) {
return ! _.isEmpty(str);
}
function not(x) { return !x; }

var notEmpty = _.compose(not, _.isEmpty);
notEmpty('foo'); // true
notEmpty(''); // false
notEmpty(); // false
notEmpty(null); // false
function findMaxForCollection(data) {
var items = _.pluck(data, 'val');
return Math.max.apply(null, items);
}

var data = [{id: 1, val: 5}, {id: 2, val: 6}, {id: 3, val: 2}];

findMaxForCollection(data);
var findMaxForCollection = _.compose(function(xs) { 
return Math.max.apply(null, xs);
}, _.pluck);

var data = [{id: 1, val: 5}, {id: 2, val: 6}, {id: 3, val: 2}];

findMaxForCollection(data, 'val'); // 6
function pluck(key) {
return function(collection) {
return _.pluck(collection, key);
}
}
function max(xs) {
return Math.max.apply(null, xs);
}
var findMaxForCollection = _.compose(max, pluck('val'));

findMaxForCollection(data);
function plucked(key, collection) {
return _.pluck(collection, key);
}

var pluck = _.curry(plucked);
function max(xs) {
return Math.max.apply(null, xs);
}

function plucked(key, collection) {
return _.pluck(collection, key);
}

var pluck = _.curry(plucked);

var findMaxForCollection = _.compose(max, pluck('val'));

var data = [{id: 1, val: 5}, {id: 2, val: 6}, {id: 3, val: 2}];

findMaxForCollection(data); // 6
var findMaxForCollection = _.compose(max, pluck('val'));
var data = [{id: 1, val: 5, active: true}, 
{id: 2, val: 6, active: false },
{id: 3, val: 2, active: true }];
function getMaxIdForActiveItems(data) {
var filtered = _.filter(data, function(item) {
return item.active === true;
});

var items = _.pluck(filtered, 'val');
return Math.max.apply(null, items);
}
var getMaxIdForActiveItems = _.compose(max, pluck('val'), _.filter);

getMaxIdForActiveItems(data, function(item) {
return item.active === true;
}); // 5
function filter(fn) {
return function(arr) {
return arr.filter(fn);
};
}
function isActive(item) {
return item.active === true;
}
var getMaxIdForActiveItems = 
_.compose(max, pluck('val'), filter(isActive));
getMaxIdForActiveItems(data); // 5
var isNotActive = _.compose(not, isActive);

var getMaxIdForNonActiveItems = _.compose(max, pluck('val'), filter(isNotActive));

Roundup

Links


JavaScript Inside

All things JavaScript.

Welcome to a place where words matter. On Medium, smart voices and original ideas take center stage - with no ads in sight. Watch
Follow all the topics you care about, and we’ll deliver the best stories for you to your homepage and inbox. Explore
Get unlimited access to the best stories on Medium — and support writers while you’re at it. Just $5/month. Upgrade

Get the Medium app

A button that says 'Download on the App Store', and if clicked it will lead you to the iOS App store
A button that says 'Get it on, Google Play', and if clicked it will lead you to the Google Play store