javascript之Partial Application学习


Posted in Javascript onJanuary 10, 2013

这一次来学习一下Partial Application。我们先看一下函数的介绍,在维基上有简单的介绍:
在数学中,一个函数是描述每个输入值对应唯一输出值的这种对应关系,符号为 f(x)。例如,表达式 f(x)=x2表示了一个函数 f,其中每个输入值x都与唯一输出值x2相联系。

因此,如果一个输入值为3,那么它所对应的输出值为9。而g(x,y) = xy有两个参量x和y,以乘积xy为值。上面描述了函数(为方便假设x,y都是int),并且给出了函数的两个例子,先换一种方式来看,f(x)可以表示为:x -> y(x2),即经经过f到x2的映射,写成 int -> int。

接受一个int 返回一个int。再看g(x,y)可以表示为:x -> y -> z(xy)。即x,y经过g的映射到z,写成 int -> int -> int。我们看g(x,y)函数,用javascript来实现一下:

function g(x,y){ 
return x*y; 
}

很完美啊,很接近数学定义。它依次接受两个参数,x与y。并且返回它们两个的乘积。但是当x是个常数,比如x=n(n是一个自然数)。那么g(n,y)=ny。这就变成一个常数与一个变量的乘积,它接受一个参数y返回ny,即y -> z(ny) 的映射,写成 int -> int。因此,我们可以这样来理解上面的工作,g(x,y)是接受一个参数int,并且返回一个函数 int ->int 。这个返回的函数只接受一个int 并且返回一个int。来用javascript表示一下:
var h = g(2);

这里的h表示函数h(y)=2y。这样就有h(5)=10,h(13)=26等。
h(5); 
h(13);

这个技术是把需要多个参数的函数形式转变为接受单个参数的函数链,它通常叫做Curring,这是为了纪念Haskell Curry而起的名字,但他并不是第一个提出的1。但是很遗憾的是javascript并不支持这样的特性。所以要实现这样的特性需要做一些工作,这些工作并不复杂。主要是把参数存储起来,等待调用函数链上的下一个函数时拿出前边参数继续传递给链上的下一个函数,直到最后得到返回值。先看一下下面的代码:
function atarr(a,index){ 
var index=index||0,args = new Array(a.length - index); 
for(var i in a){ 
if(i>=index) args[i-index]=a[i]; 
} 
return args; 
} 
function m(scope,fn){ 
if(arguments.length<3) return fn.call(scope); 
var p = atarr(arguments,2); 
return function(){ 
var args = atarr(arguments); 
return fn.apply(scope,p.concat(args)); 
} 
}

测试代码:
var plus = function(a,b){ 
return a+b; 
}; 
var plus2 = m(null,plus,2); 
console.log(plus2(10)); 
console.log(plus2(0)); 
//结果 
12 
2

这样我们的目标已经实现啦。在上面的atarr函数是将arguments对象中指定位置开始的参数取出并且保存到一个数组中。m函数就是主角,它完成了前面定义的任务,实现了保存函数链上的参数并且返接受余下参数的函数。测试代码中的plus函数原先接受a,b两个参数并返回a与b之和,即 int -> int -> int,而plus2则变成了接受一个参数b与2相加,并返回2与b之和,即 int -> int。

通过上面的一些工作,我们实现了javascript中的Partial Application,在dojo框架中hitch2实现了域绑定和partial。有兴趣可以读一下它的源码,也是非常简单明了的。

Javascript 相关文章推荐
css3元素简单的闪烁效果实现(html5 jquery)
Dec 28 Javascript
JavaScript中的typeof操作符用法实例
Apr 05 Javascript
javascript制作网页图片上实现下雨效果
Feb 26 Javascript
javascript日期比较方法实例分析
Jun 17 Javascript
jquery实现提示语淡入效果
May 05 jQuery
vue2.0 路由不显示router-view的解决方法
Mar 06 Javascript
基于layui数据表格以及传数据的方式
Aug 19 Javascript
node.js连接mysql与基本用法示例
Jan 05 Javascript
vue-cli构建vue项目的步骤详解
Jan 27 Javascript
Vue实现搜索结果高亮显示关键字
May 28 Javascript
小程序分享链接onShareAppMessage的具体用法
May 22 Javascript
Vue路由切换页面不更新问题解决方案
Jul 10 Javascript
javascript之典型高阶函数应用介绍二
Jan 10 #Javascript
javascript之典型高阶函数应用介绍
Jan 10 #Javascript
根据json字符串生成Html的一种方式
Jan 09 #Javascript
web的各种前端打印方法之jquery打印插件jqprint实现网页打印
Jan 09 #Javascript
web的各种前端打印方法之jquery打印插件PrintArea实现网页打印
Jan 09 #Javascript
实现web打印的各种方法介绍及实现代码
Jan 09 #Javascript
js去除重复字符串两种实现方法
Jan 09 #Javascript
You might like
PHP parse_url 一个好用的函数
2009/10/03 PHP
PHP MemCached高级缓存配置图文教程
2010/08/05 PHP
PHP执行批量mysql语句的解决方法
2013/05/02 PHP
PHP对XML内容进行修改和删除实例代码
2016/10/26 PHP
Ubuntu中支持PHP5与PHP7双版本的简单实现
2018/08/19 PHP
php实现小程序支付完整版
2018/10/09 PHP
php源码的使用方法讲解
2019/09/26 PHP
关于IFRAME 自适应高度的研究
2006/07/20 Javascript
PJ Blog修改-禁止复制的代码和方法
2006/10/25 Javascript
JS 常用校验函数
2009/03/26 Javascript
超简单JS二级、多级联动的简单实例
2014/02/18 Javascript
javascript算法题:求任意一个1-9位不重复的N位数在该组合中的大小排列序号
2015/04/01 Javascript
深入解读JavaScript中的Iterator和for-of循环
2015/07/28 Javascript
详解JavaScript数组的操作大全
2015/10/19 Javascript
jquery实现简易的移动端验证表单
2015/11/08 Javascript
微信小程序 连续旋转动画(this.animation.rotate)详解
2017/04/07 Javascript
Vue中常用rules校验规则(实例代码)
2019/11/14 Javascript
node.js中stream流中可读流和可写流的实现与使用方法实例分析
2020/02/13 Javascript
javascript实现搜索筛选功能实例代码
2020/11/12 Javascript
Python文件和目录操作详解
2015/02/08 Python
Python下的subprocess模块的入门指引
2015/04/16 Python
Django中login_required装饰器的深入介绍
2017/11/24 Python
python 获取指定文件夹下所有文件名称并写入列表的实例
2018/04/23 Python
pyautogui自动化控制鼠标和键盘操作的步骤
2020/04/01 Python
Marmot土拨鼠官网:美国专业户外运动品牌
2018/01/11 全球购物
Parfume Klik丹麦:香水网上商店
2018/07/10 全球购物
世界领先的豪华床上用品供应商之一:Bedeck Home
2019/03/18 全球购物
自我鉴定的范文
2013/10/03 职场文书
护士演讲稿范文
2014/01/05 职场文书
适用于所有创业者的创业计划书
2014/02/05 职场文书
广告传媒专业应届生求职信
2014/03/01 职场文书
信电学院毕业生自荐书
2014/05/24 职场文书
三分钟自我介绍演讲稿
2014/08/21 职场文书
了解Redis常见应用场景
2021/06/23 Redis
Python 正则模块详情
2021/11/02 Python
MySQL派生表联表查询实战过程
2022/03/20 MySQL