JavaScript 函数柯里化(currying)

原创 lingwer111 随笔 JavaScript 269阅读 2017-05-07 20:59:32 举报

前言
2个月前看面试题的时候,遇到这样的一个题目。

JavaScript函数柯里化(currying)
于是很自信的写下的这样的代码。也顺利通过检测,利用闭包来完成信息的返回。
html 代码

代码可以通过检测,但并不完美。这是初级工程师水平(3K)的代码。需求是经常变化的,加入有一天需求改为传入3个参数甚至更多的。这代码就报废了。看到了别人的高逼格代码,水平很高。
html 代码

这段代码可以接受N个传参,连续研究了几晚也没看懂是什么。有点小失落,这是初级工程师(3K)和高级工程师(30K)的差距啊。直到最近看《JavaScript 设计模式与开发实践》提及,高阶函数介绍中的函数柯里化(currying),才恍然大悟。

介绍
柯里化(curyying)的概念最早是由俄罗斯数学家Mose SchoinfinKel发明,后来由著名的数理学家Haskell Curry将其丰富和拓展,curryying由此得名。
柯里化又称部分求值,一个柯里化的函数首先会接受一些传参,接受了这些传参之后,改函数并不会立即求值,而是继续返回另外一个函数,刚才传入的参数在函数内形成的闭包中被保存起来,到参数被真正求值的时候,之前传入的参数会被一次性用于求值。
从字面上理解currying并不太容易,下面来看一个例子

假设我们要编写一个计算每月开销的函数,在每天结束之前,我们都要记录今天花掉了多岁钱,代码如下
javascript 代码

这段代码可以看到,每天结束后我们都会记录并计算到今天为止花掉的钱,但我们其实并不太关系每天花掉的钱,而只想在月底的时候知道这一个月花销的总数,也就是说实际上只需要计算一次

下面的代码还不是currying函数的完整实现,但有助于我们了解其思想
javascript 代码

接下来我们编写一个通用的 function currying(){}。 它接受一个参数,即将要被currying的函数,在这里例子里,这个函数的作用遍历本月每天的开销并求出他们的总和。代码如下
javascript 代码

至此。我们完成了一个柯里化函数的编写,当调用cost时,如果明确地带上了一些参数,表示此时并不真正进行求值运算。而是把一些参数保存起来,此时让cost函数返回另外一个函数,只有当我们以不带参数的形式执行cost()时,才利用前面保存的所有参数,真正开始进行求值运算。

如果要将记录每月花销这道题的传参形式改成题目开始时的链式传参。可以这样写
javascript 代码

文章开头哪里传字符串的柯里化函数比较复杂,这里有一个简洁版的,也可以接受N个参数,柯里化是一个编程思想。有多种的编程的风格
javascript 代码

评论 ( 0 )
最新评论
暂无评论

赶紧努力消灭 0 回复