Function First With Native Methods
I keep seeing lodash and UnderscoreJS fighting for popularity, but every time I see either library mentioned, I can’t help but think back to Brian Lonsdorf’s great talk Hey Underscore, You’re Doing It Wrong!.
Brian focused on a particular signature choice in UnderscoreJS that places the receiver, or context object, at the first position of the “functional-style” method call:
Without saying which way is ‘right’, I have found both patterns helpful at different times. So, I wrote this little utility to create several functions from native methods with both signatures available.
Because currying is awesome, these functions curry. But they curry the ‘right’ way, not the ‘optional’ way. (Ok, now I’m starting to have an opinion.) This produces “function butts.” Although you can deal with function butts for this dose of awesomeness.
In addition to currying and working within a functional style, Cody Lindley points out another great benefit of these functions is their ability to operate on array-like objects as well as native arrays.
“But wait, there’s more!” As Nathal Wall pointed out, in his talk on High Integrity JavaScript, when you cache copies of native functions, your code becomes resilient to disruption by anarchists and heathens who feel it necessary to modify the built-ins (you might sense my strong feelings on this subject).
Lastly, I struggled with what to call the “flipped” functions. Since, I believe, like Lonsdorf and other functional languages, that function-first is ‘right’, I settled on the “To” suffix. This assumes the process to be read as “apply to X” or “map function to list.”
Naturally, if you have your own, strong, feelings on the subject, you’re welcome to fork or copy the gist and make it your own.
This produces:
- each - each(fn)(arr)
- eachTo - eachTo(arr)(fn)
- map - map(fn)(arr)
- mapTo - mapTo(arr)(fn)
- filter - filter(fn)(arr)
- filterTo - filterTo(arr)(fn)
- some - some(fn)(arr)
- someTo - someTo(arr)(fn)
- every - every(fn)(arr)
- everyTo - everyTo(arr)(fn)
- reduce - reduce(fn)(arr)
- reduceTo - reduceTo(arr)(fn)
- reduceRigth - reduceRight(fn)(arr)
- reduceRigthTo - reduceRightTo(arr)(fn)
Here are some tests you can copy/paste into the console.