概念
函数式编程是一种编程范式,主要是利用函数把运算过程封装起来,通过组合各种函数来处理数据,通过串联多个函数来计算,类似一条流水线。
特点
函数是一等公民
函数与其他数据类型一样,处于平等地位,可以赋值给变量,可以作为函数入参或者返回值。
ajaxCall(json => callback(json)); // 脱裤子放P// 等价于这行ajaxCall(callback);
高阶函数: 把函数作为参数或者返回值的一类函数。
声明式编程
声明式编程关心做什么,命令式编程关心怎么做
// 命令式var makes = [];for (i = 0; i < cars.length; i++) {makes.push(cars[i].make);}// 声明式var makes = cars.map(function(car){ return car.make; });
纯函数
- 无状态:函数的输出仅取决于输入,而不依赖外部状态;
 - 无副作用: 不修改外部状态,不修改入参。
 
意味着相同的输入,永远会得到相同的输出。
var xs = [1,2,3,4,5];// 纯的xs.slice(0,3);//=> [1,2,3]// 不纯的xs.splice(0,3); //改变原数组//=> [1,2,3]
其他优点:
- 可缓存性,因为相同的输入得会得到相同的输出,那么可以缓存函数的结果。
 - 可移植性/自文档化,纯函数的依赖很明确,因此更易于观察和理解
 - 可测试性,函数让测试更加简单,只需简单地给函数一个输入,然后断言输出就可以了。
 - 引用透明性,如果一段代码可以替换成它执行所得的结果,而且是在不改变整个程序行为的前提下替换的,那么我们就说这段代码是引用透明的。
柯里化(curry)
柯里化的意思是将一个多元函数,转换成一个依次调用的单元函数。
柯里化函数会接收一些参数,然后不会立即求值,而是继续返回一个新函数,将传入的参数通过闭包的形式保存,等到被真正求值的时候,,再进行求值。 ```javascript var add = function(x) { return function(y) { return x + y; }; }; const increment = add(1);f(a,b,c) → f(a)(b)(c)
 
increment(10); // 11
<a name="cxOSF"></a>### 偏函数> **偏函数** ( Partial )是指固定一个函数的一些参数,然后产生另一个更小元的函数。> In computer science, partial application(or partial function application) refers to the process of fixing a number of arguments to a function, producing another function of smaller arity.- 柯里化:将多参数函数转换成多个单参数函数,也就是将一个 n 元函数转换成 n 个一元函数- 偏函数:则是固定一个函数的一个或多个参数,也就是将一个 n 元函数转换成一个 n - x 元函数```javascript// 柯里化f(a,b,c) → f(a)(b)(c)// 偏函数f(a,b,c) → f(a)(b,c) / f(a,b)(c)
组合(compose)
函数组合的目的是将多个函数组合成一个函数
const compose = (f, g) => x => f(g(x))const f = x => x + 1;const g = x => x * 2;const fg = compose(f, g);fg(1) //3
function compose(...fns) {return fns.reduce((a,b) => {return (...args) => {return a(b(...args))}})}function fn1(a) {console.log('fn1: ', a);return a+1}function fn2(a) {console.log('fn2: ', a);return a+1}function fn3(a) {console.log('fn3: ', a);return a+1}console.log(compose(fn1, fn2, fn3)(1));
参考
简明 JavaScript 函数式编程——入门篇—网易云
浅析JavaScript函数式编程—转转
《函数式编程指北》中文翻译
https://juejin.cn/post/6844903909169823751
