zoukankan      html  css  js  c++  java
  • js函数式编程-函数合成和柯里化

    函数式编程有2个最基本的运算:合成(compose)和柯里化(currying)

    合成:如果一个值要经过多个函数才能编程另一个值,那么我们可以把中间的步骤合并成一个函数,这个叫做函数的合成

    函数的合成我们采用es6的reduce方法,先举一个小例子说明reduce的特性

    const arr = [1,2,3,4]
    let a = arr.reduce(function(total,next){
        return total+next
    })
    console.log(a) //10

    可以看到,reduce接收一个函数,函数的两个参数分别代表了累加返回值和下一个要处理的值,我们用reduce最多的场景是用它来求和。那么如果我们把arr数组换成函数数组,在reduce里一层一层的执行函数不就可以实现函数的合成了嘛。

    下面我们把上边的数字组成的数组换成函数组成的数组,再用一个函数包装一下reduce函数

    function f1(arg){
        console.log("f1",arg)
        return arg;
    }
    function f2(arg){
        console.log("f2",arg)
        return arg;
    }
    function f3(arg){
        console.log("f3",arg)
        return arg;
    }
    function compose(...funcs){
        if(funcs.length===0){
            return arg=>arg;
        }
        if(funcs.length===1){
            return funcs[0];
        }
        // return funcs.reduce((a,b)=>(...args)=>a(b(...args)))
        return funcs.reduce(function(a,b){
            return function(o){
                return a(b(o))
            }
        })
    }
    let res = compose(f1,f2,f3)("omg");//f1(f2(f3("omg"))) 洋葱模型
    console.log("res",res);

    打印结果:

    f3 omg
    f2 omg
    f1 omg
    res omg

    可以看到上面的compose函数接收了一个函数数组,函数里面reduce的部分有点绕,我们逐步讲解一下,首先,compose函数需要返回一个reduce函数处理过的值,reduce函数接收一个函数作为参数,这个函数的第一个参数a就相当于上面累加例子里的total,b就相当于下一个要执行的函数。到这里其实就结束了,但是我们将来还需要给函数传递参数,比如传入了一个omg字符串,那么我们希望compose函数返回值也是一个函数,我们才能在调用的时候再传递参数。所以我们在里面再套一层函数来接收参数o。

    上面的compose最终的目的是实现了一个像洋葱的函数调用形式,一层包着一层 f1(f2(f3("omg")))

    柯里化:把接收多个参数的函数变成接收一个参数的函数,并且返回接收余下参数而且返回结果的新函数

    举个例子说明一下柯里化后的函数和之前的有什么不同

    // curry之前
    function add(x,y){
        return x+y
    }
    add(1,2)
    
    // curry之后
    function newAdd(x){
        return function(y){
            return x+y
        }
    }
    let aa = newAdd(1)(2)
    console.log(aa)

    可以看到函数的柯里化就是利用闭包的特性,记住参数,然后返回一个函数,函数的返回值是最终的结果,经过柯里化的函数我们的调用会更加灵活

    那么有小伙伴问了,这个函数究竟灵活在哪里了呀?

    我感觉主要是柯里化提高了函数的适用性,我们可以想用什么功能就传递什么参数,根据传入参数的数量实现函数的随取随用。增加了代码的复用性。

    更多函数式编程知识参见:https://llh911001.gitbooks.io/mostly-adequate-guide-chinese/content/ch1.html#%E4%BB%8B%E7%BB%8D

  • 相关阅读:
    可恶的0x1A
    求关注 wcf bindipendpointdelegate 端口限制的功能
    2015 UESTC Training for Data Structures
    Codeforces Round #298 (Div. 2)
    利用rawcap抓包(自己发给自己的包裹)
    PYTHON POST练手
    CentOS安装Nginx 实现HTTP代理
    how to make vim show ^M and substitute it
    Oracle SQL Developer: cannot find a j2se sdk
    Codeforces Round #282 (Div. 2)
  • 原文地址:https://www.cnblogs.com/panda-programmer/p/13399659.html
Copyright © 2011-2022 走看看