Reputation: 53017
If you try to program in a functional style on JavaScript, you'll probably realize the conventional fn(obj,params...)
form gets unreadable fast.
console.log(
join(
map(function(row){ return row.join(" "); },
format(
map(function(text){return align(text},
view),
20))),
"\n");
VS
view.map(function(text){return align(text)})
.format(20)
.map(function(row){return row.join(" ");})
.join("\n")
.log();
Problematically, the latter style could only be implemented extending the Object.prototype
with new functions, which is globally regarded as evil. Yet, the readability is so superior that I'm prompted to just go ahead and do it anyway. Is there a better way to solve this problem?
Upvotes: 0
Views: 2104
Reputation: 5909
Yes, there is a better way to solve the problem. Below is a demonstration using lodash.
Bad method:
import _ from "lodash";
_.chain([1, 2, 3])
.map(x => [x, x*2])
.flatten()
.sort()
.value();
Better method:
import map from "lodash/fp/map";
import flatten from "lodash/fp/flatten";
import sortBy from "lodash/fp/sortBy";
import flow from "lodash/fp/flow";
flow(
map(x => [x, x*2]),
flatten,
sortBy(x => x)
)([1,2,3]);
See Why using _.chain
is a mistake. for a fantastic, in-depth explanation.
Upvotes: 2
Reputation: 146084
The basic pattern is
this
this
, then return this
.http://jsfiddle.net/XjRrn/ is a working example:
function ChainableArray(rawArray) {
this._array = rawArray || [];
};
ChainableArray.prototype.map = function(fn) {
this._array = _.map(this._array, fn);
return this;
};
ChainableArray.prototype.incr = function(amount) {
this._array = _.map(this._array, function (item) {return item + amount;});
return this;
};
ChainableArray.prototype.toArray = function () {
return _.clone(this._array);
};
The Query object from the mongoose.js library is a great case study to reference.
Upvotes: 1
Reputation: 215009
A common "monadic" approach to this is to wrap an operand into your own object, call a chain of methods on that object and then extract the plain value back. Example from underscore.js docs:
var youngest = _.chain(stooges)
.sortBy(function(stooge){ return stooge.age; })
.map(function(stooge){ return stooge.name + ' is ' + stooge.age; })
.first()
.value();
Upvotes: 1