关于原生js中bind函数的简单实现


Posted in Javascript onAugust 10, 2016

今天继续研究了bind函数的实现,也知道了shim和polyfill的说法,现在总结一下,

if (!Function.prototype.bind) {
 Function.prototype.bind = function (oThis) {
  if (typeof this !== "function") {
   // closest thing possible to the ECMAScript 5 internal IsCallable function
   throw new TypeError("Function.prototype.bind - what is trying to be bound is not callable");
  }

  var aArgs = Array.prototype.slice.call(arguments, 1), 
    fToBind = this, 
    fNOP = function () {},
    fBound = function () {
     return fToBind.apply(this instanceof fNOP && oThis
                 ? this
                 : oThis || window,
                aArgs.concat(Array.prototype.slice.call(arguments)));
    };

  fNOP.prototype = this.prototype;
  fBound.prototype = new fNOP();

  return fBound;
 };
}

这是官方文档上的实现,我分二个方面来谈我要说的东西,

第一个是参数,agruments的使用

var aArgs = Array.prototype.slice.call(arguments, 1),这里是将bind函数的参数数组取出来,第一个参数不要(就是不要oThis)也就是要被绑定方法的那个对象,第二个是

aArgs.concat(Array.prototype.slice.call(arguments))); 这里是用了数组的方法,把参数插在参数数组后面,要注意,这个函数是要被return 出去然后执行的,他的参数数组是return出去的那个fBound函数的参数数组,所以上下两个参数数组是不一样的,有点像柯里化。

第二个是上下文,在其中上下文的变化比较难理解,bind函数主要就是为了绑定上下文来使用的

fToBind = this 这里是保存了对象的上下文,紧接着下面的apply方法让要被绑定的那个对象可以使用该上下文

fNOP.prototype = this.prototype;

fBound.prototype = new fNOP();

这里是以fNOP为中介把this.prototype这个原对象的属性给fBound,确保fBound是在定义的时候的那个上下文里面执行。本来

bound.prototype = self.prototype就可以将原属性集成过来了,但是这样两个对象属性都指向同一个地方,修改 bound.prototype 将会造成self.prototype 也发生改变,这样并不是我们的本意。所以通过一个空函数 nop 做中转,能有效的防止这种情况的发生。

以上这篇关于原生js中bind函数的简单实现就是小编分享给大家的全部内容了,希望能给大家一个参考,也希望大家多多支持三水点靠木。

Javascript 相关文章推荐
JS多物体 任意值 链式 缓冲运动
Aug 10 Javascript
js 延迟加载 改变JS的位置加快网页加载速度
Dec 11 Javascript
JQuery切换显示的效果实例代码
Feb 27 Javascript
js实现图片漂浮效果的方法
Mar 02 Javascript
javascript 动态创建表格的2种方法总结
Mar 04 Javascript
浅谈node.js中async异步编程
Oct 22 Javascript
详解vuex 中的 state 在组件中如何监听
May 23 Javascript
D3.js实现拓扑图的示例代码
Jun 30 Javascript
详解性能更优越的小程序图片懒加载方式
Jul 18 Javascript
Vue监听事件实现计数点击依次增加的方法
Sep 26 Javascript
在Web关闭页面时发送Ajax请求的实现方法
Mar 07 Javascript
vue+element-ui+axios实现图片上传
Aug 20 Javascript
Mvc提交表单的四种方法全程详解
Aug 10 #Javascript
mvc中form表单提交的三种方式(推荐)
Aug 10 #Javascript
浅谈JS运算符&&和|| 及其优先级
Aug 10 #Javascript
浅谈jQuery中的checkbox问题
Aug 10 #Javascript
jQuery实现将div中滚动条滚动到指定位置的方法
Aug 10 #Javascript
Three.js学习之网格
Aug 10 #Javascript
js 将图片连接转换成base64格式的简单实例
Aug 10 #Javascript
You might like
php合并数组array_merge函数运算符加号与的区别
2008/10/31 PHP
eaglephp使用微信api接口开发微信框架
2014/01/09 PHP
自己写的兼容低于PHP 5.5版本的array_column()函数
2014/10/24 PHP
phpstorm配置Xdebug进行调试PHP教程
2014/12/01 PHP
PHP实现的进度条效果详解
2016/05/03 PHP
ThinkPHP框架整合微信支付之Native 扫码支付模式一图文详解
2019/04/09 PHP
javascript判断单选框或复选框是否选中方法集锦
2007/04/04 Javascript
js创建子窗口并且回传值示例代码
2013/07/02 Javascript
js 加密压缩出现bug解决方案
2014/11/25 Javascript
js闭包实现按秒计数
2015/04/23 Javascript
javascript实现可拖动变色并关闭层窗口实例
2015/05/15 Javascript
详解JavaScript基于面向对象之创建对象(2)
2015/12/10 Javascript
移动端 一个简单易懂的弹出框
2016/07/06 Javascript
jQuery实现验证码功能
2017/03/17 Javascript
NodeJS处理Express中异步错误
2017/03/26 NodeJs
AngularJS日期格式化常见操作实例分析
2018/05/17 Javascript
JavaScript从原型到原型链深入理解
2019/06/03 Javascript
vue iview的菜单组件Mune 点击不高亮的解决方案
2019/11/01 Javascript
JS严格模式原理与用法实例分析
2020/04/27 Javascript
[01:03:38]2014 DOTA2国际邀请赛中国区预选赛5.21 CNB VS CIS
2014/05/22 DOTA
[01:00:06]加油DOTA_EP01_网络版
2014/08/09 DOTA
go和python调用其它程序并得到程序输出
2014/02/10 Python
在Python中利用Into包整洁地进行数据迁移的教程
2015/03/30 Python
在Linux下调试Python代码的各种方法
2015/04/17 Python
pandas把所有大于0的数设置为1的方法
2019/01/26 Python
使用Python实现毫秒级抢单功能
2019/06/06 Python
PyQt5笔记之弹出窗口大全
2019/06/20 Python
Python基于unittest实现测试用例执行
2020/11/25 Python
美国领先的水果篮送货公司和新鲜水果供应商:The Fruit Company
2018/02/13 全球购物
EJB发布WEB服务一般步骤
2012/10/31 面试题
火锅店营销方案
2014/02/26 职场文书
元旦晚会感言
2014/03/12 职场文书
党校培训自我鉴定范文
2014/03/20 职场文书
2014年纪委工作总结
2014/12/05 职场文书
实习指导老师意见
2015/06/04 职场文书
2016个人廉洁自律承诺书
2016/03/25 职场文书