纯函数和柯里化很容易写出洋葱代码,函数组合就可以把细粒度的函数重新组合成一个新的函数。
函数组合案例:
function compose (fn1, fn2){
return function(value){
return fn1(fn2 ( value ));
}
}
function reverse (array){
return array.reverse()
}
function first (array){
return array[0]
}
const last = compose(first,reverse);
let arr = [1,2,3,4,5,6];
console.log(last(arr));
Lodash中的函数组合flow,flowRight:
const _ = require('lodash');
const reverse = arr => arr.reverse();
const first = arr => arr[0];
const toUpper = arr => arr.toUpperCase();
const fn =_.flowRight(toUpper,first,reverse);
console.log(fn(['one','two','three']));
手写lodash中的flowRight:
const reverse = arr => arr.reverse();
const first = arr => arr[0];
const toUpper = arr => arr.toUpperCase();
// const fn =_.flowRight(toUpper,first,reverse);
// 模拟 lodash 中的 flowRight
// function compose (...args) {
// return function (value) {
// return args.reverse().reduce(function (acc, fn) {
// return fn(acc)
// }, value)
// }
// }
const compose = (...args) => value => args.reverse().reduce((acc, fn) => fn(acc), value)
const f = compose(toUpper, first, reverse)
console.log(f(['one', 'two', 'three']))
函数组合要满足结合律
如果我们组合的函数,跟我们预期的结果不一致,要怎么调试呢
const _ = require('lodash');
let target = 'NEVER SAY DIE';
const log = _.curry((tag ,v) =>{
console.log(tag + v);
return v;
})
const split = _.curry((sep , str) => _.split(str, sep));
const join = _.curry((sep ,arr) => _.join(arr, sep));
const f = _.flowRight(_.toLower,log('join:'),join('-'),log('split:'),split(' '));
console.log(f(target));
lodash中的fp模块,也就是function programming模块,是ladash针对函数式编程的模块。
lodash中的fp模块,函数优先,参数滞后。
二、PointFree
我们可以把数据处理的过程定义成与数据无关的合成运算,不需要用到代表数据的那个参数,
只要把简单的运算步骤合成到一起,在使用这个模式之前我们需要定义一些辅助的基本运算函数。
1、我们不要指明处理的数据
2、我们只需要合成运算过程
3、需要定义一些辅助的基本运算函数
案例:
const fp = require('lodash/fp')
// Hello World => hello_world
const f = fp.flowRight(fp.replace(/\s+/g, '_'), fp.toLower)
console.log(f('Hello World'))
// world wild web ==> W. W. W
const firstLetterToUpper = fp.flowRight(fp.join('. '), fp.map(fp.flowRight(fp.first, fp.toUpper)), fp.split(' '))
console.log(firstLetterToUpper('world wild web'))