要求写一个函数add(),分别实现能如下效果:

(1)console.log(add(1)(2)(3)(4)());//
(2)console.log(add(1,2)(3,4)());//
(3)console.log(add(1,2)(3,4));//

针对(1)和(2),有两种思路实现:纯闭包思路和函数柯里化思路。

一、闭包思路

(1)的解决方案(闭包实现)

function add(arg) {
// body...
let sum = 0;
sum+=arg;
return function (tmarg) {
// body...
if (arguments.length == 0) {
return sum;
}else{
sum+=tmarg;
return arguments.callee;
}
}
}

(2)的解决方案

function add(arg) {
// body...
let sum = 0;
sum = Array.prototype.slice.call(arguments).reduce((a,b) => {return a+b;},sum);
return function (tmarg) {
// body...
if (arguments.length == 0) {
return sum;
}else{
sum = Array.prototype.slice.call(arguments).reduce((a,b) => {return a+b;},sum);
return arguments.callee;
}
}
}

二、函数柯里化的思路

通俗的理解,由于函数柯里化具有这样的特性:它能够"积累"函数的参数(不管是foo(1,2,3)还是foo(1)(2)(3)这种链式形式)),并且延迟执行。可以将多个参数积累到一个数组中,在最后一步执行求和。
柯里化通用形式:

function curry(fn) {
// body...
var args = Array.prototype.slice.call(arguments,1);
return function () {
// body...
var innerArgs = Array.prototype.slice.call(arguments);
var finalArgs = args.concat(innerArgs);
console.log(finalArgs);
return fn.apply(null,finalArgs);
};
}

(2)的解决方案:

function add() {
let sum = 0;
var _args = Array.prototype.slice.call(arguments);
var tmpf = function(){
if(arguments.length === 0) {
sum = _args.reduce((a,b) => {return a + b;},sum);
}
_args.push.apply(_args,[].slice.call(arguments));
return tmpf;
}
}

针对问题(3):

function add(arg) {
// body...
let sum = 0;
sum = Array.prototype.slice.call(arguments).reduce((a,b) => {return a+b;},sum);
var tmpf = function (tmarg) {
// body...
if (arguments.length == 0) {
return sum;
}else{
sum = Array.prototype.slice.call(arguments).reduce((a,b) => {return a+b;},sum);
return tmpf;
}
};
tmpf.toString = tmpf.valueOf = function () {
// body...
return sum;
}
return tmpf;
}

完!

转载请注明原文出处:http://www.cnblogs.com/qcblog/p/6858947.html

一道javascript面试题(闭包与函数柯里化)的更多相关文章

  1. Javascript函数柯里化(curry)

    函数柯里化currying,是函数式编程非常重要的一个标志.它的实现需要满足以下条件,首先就是函数可以作为参数进行传递,然后就是函数可以作为返回值return出去.我们依靠这个特性编写很多优雅酷炫的代 ...

  2. 深入理解javascript函数进阶系列第二篇——函数柯里化

    前面的话 函数柯里化currying的概念最早由俄国数学家Moses Schönfinkel发明,而后由著名的数理逻辑学家Haskell Curry将其丰富和发展,currying由此得名.本文将详细 ...

  3. 简单粗暴详细讲解javascript实现函数柯里化与反柯里化

    函数柯里化(黑人问号脸)???Currying(黑人问号脸)???妥妥的中式翻译既视感:下面来一起看看究竟什么是函数柯里化: 维基百科的解释是:把接收多个参数的函数变换成接收一个单一参数(最初函数的第 ...

  4. JavaScript中的事件循环机制跟函数柯里化

    一.事件循环机制的理解 test();//按秒输出5个5 function test() { for (var i = 0; i < 5; i++) { setTimeout(() => ...

  5. JavaScript函数柯里化的一些思考

    1. 高阶函数的坑 在学习柯里化之前,我们首先来看下面一段代码: var f1 = function(x){ return f(x); }; f1(x); 很多同学都能看出来,这些写是非常傻的,因为函 ...

  6. 精读JavaScript模式(六),Memoization模式与函数柯里化的应用

    假期就这么结束了!十天假就有三天在路上,真的难受!想想假期除了看了两场电影貌似也没做什么深刻印象的事情.流浪地球,特效还是很赞,不过对于感情的描写还是逃不掉拖沓和尴尬的通病,对于国产科幻还是抱有支持的 ...

  7. 简单粗暴详细讲解javascript实现函数柯里化

    函数柯里化(黑人问号脸)???Currying(黑人问号脸)???妥妥的中式翻译既视感:下面来一起看看究竟什么是函数柯里化: 维基百科的解释是:把接收多个参数的函数变换成接收一个单一参数(最初函数的第 ...

  8. Scala 基础(十二):Scala 函数式编程(四)高级(二)参数(类型)推断、闭包(closure)、函数柯里化(curry)、控制抽象

    1  参数(类型)推断 参数推断省去类型信息(在某些情况下[需要有应用场景],参数类型是可以推断出来的,如list=(1,2,3) list.map() map中函数参数类型是可以推断的),同时也可以 ...

  9. JavaScript之函数柯里化

    什么是柯里化(currying)? 维基百科中的解释是:柯里化是把接受多个参数的函数变换成接受一个单一参数(最初函数的第一个参数)的函数,并且返回接受余下的参数而且返回结果的新函数的技术.意思就是当函 ...

随机推荐

  1. 小程序脚本语言WXS详解

    WXS脚本语言是 Weixin Script脚本的简称,是JS.JSON.WXML.WXSS之后又一大小程序内部文件类型.截至到目前小程序已经提供了5种文件类型. 解构小程序的几种方式,其中一种方式就 ...

  2. sqlserver 父子级查询(理念适应所有数据库)

    实现技术: 存储过程   ,零时表(3) 一句话说完 :把父级查询下来的子级ID 保存成零时表,并且将符合子级ID数据添加到另一张零时表. 同时清空数据时需要使用到一张零时表作为容器: alter P ...

  3. FormData 上传多种格式的文件

    <!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/ ...

  4. 结对编程1---四则运算---GUI

    201421123003 黄建英 201421123004 黄美海 题目描述: 我们在个人作业1中,用各种语言实现了一个命令行的四则运算小程序.进一步,本次要求把这个程序做成GUI(可以是Window ...

  5. 201521123042《Java程序设计》 第7周学习总结

    1. 本周学习总结 网上看了很多资料,发现这一张图总结的还不错就引用过来了.但是最上面的Map和Collection之间的关系应该是依赖,不是Produces. ①概述:Java集合框架主要包括两种类 ...

  6. 201521123020 《Java程序设计》第4周学习总结

    本周学习总结 1.1 尝试使用思维导图总结有关继承的知识点. 1.2 使用常规方法总结其他上课内容. (1)类注释的使用方法是: /** *(要注释的内容) */ (2)学习了Object类,学会了覆 ...

  7. 201521123105 第11周Java学习总结

    1. 本周学习总结 1.1 以你喜欢的方式(思维导图或其他)归纳总结多线程相关内容. 2. 书面作业 本次PTA作业题集多线程 1. 互斥访问与同步访问 完成题集4-4(互斥访问)与4-5(同步访问) ...

  8. 201521123015 《Java程序设计》第9周学习总结

    1. 本周学习总结 1.1 以你喜欢的方式(思维导图或其他)归纳总结异常相关内容. 2. 书面作业 本次PTA作业题集异常 1.常用异常 题目5-1 1.1 截图你的提交结果(出现学号) 1.2 自己 ...

  9. Eclipse rap 富客户端开发总结(4):如何搭建 rap 中文开发环境

    Rap中文开发环境搭建大约分为2个部分 1.  rap国际化,详细参加文章(rap开发经验总结(5)-rap国际化之路) 2.rap自带的JFace ,Dialog 等国际化 1.中文包下载地址: h ...

  10. Eclipse读取含有extjs的项目文件时卡死或者编写ExtJS时卡

    新建一个Eclipse或MyEclipse项目时,关掉验证. 项目右键-->Properties-->Builders--> 不勾选(JavaScript Validator.Val ...