专栏首页大数据钻研js中call、apply、bind那些事

js中call、apply、bind那些事

前言

回想起之前的一些面试,几乎每次都会问到一个js中关于call、apply、bind的问题,比如…

  1. 怎么利用call、apply来求一个数组中最大或者最小值
  2. 如何利用call、apply来做继承
  3. apply、call、bind的区别和主要应用场景

虽然网上有很多关于这方面的博客和文章,但还是决定写一篇自己对这方面知识的理解。

作用

首先问个问题,这三个函数的存在意义是什么?答案是改变函数执行时的上下文,再具体一点就是改变函数运行时的this指向。有了这个认识,接下来我们来看一下,怎么使用这三个函数。

举个栗子

 
function Person(name){

this.name = name;

}

 
Person.prototype = {

constructor: Person,

showName: function(){

console.log(this.name);

}

}

 

var person = new Person('qianlong');

person.showName();

上面的代码中person调用showName方法后会在浏览器的控制台输出qianlong

接下来

 
var animal = {

name: 'cat'

}

上面代码中有一个对象字面量,他没有所谓的showName方法,但是我还是想用?怎么办?(坑爹了,这好像在让巧媳妇去做无米之炊),不过没关系,call、apply、bind可以帮我们干这件事。

// 1 call

person.showName.call(animal);

// 2 apply

person.showName.apply(animal);

// 3 bind

person.showName.bind(animal)();

啦啦啦,有木有很神奇,控制台输出了三次cat

我们拿别人的showName方法,并动态改变其上下文帮自己输出了信息,说到底就是实现了复用

区别

上面看起来三个函数的作用差不多,干的事几乎是一样的,那为什么要存在3个家伙呢,留一个不就可以。所以其实他们干的事从本质上讲都是一样的动态的改变this上下文,但是多少还是有一些差别的..

call、apply与bind的差别

call和apply改变了函数的this上下文后便执行该函数,而bind则是返回改变了上下文后的一个函数。

call、apply的区别

他们俩之间的差别在于参数的区别,call和aplly的第一个参数都是要改变上下文的对象,而call从第二个参数开始以参数列表的形式展现,apply则是把除了改变上下文对象的参数放在一个数组里面作为它的第二个参数。


fn.call(obj, arg1, arg2, arg3...);

fn.apply(obj, [arg1, arg2, arg3...]);

应用

知道了怎么使用和他们之间的区别,接下来我们来了解一下通过call、apply、bind的常见应用场景。

  • 求数组中的最大和最小值
 
var arr = [34,5,3,6,54,6,-67,5,7,6,-8,687];

 Math.max.apply(Math, arr);

Math.max.call(Math, 34,5,3,6,54,6,-67,5,7,6,-8,687);

 Math.min.apply(Math, arr);

Math.min.call(Math, 34,5,3,6,54,6,-67,5,7,6,-8,687);
  • 将伪数组转化为数组

js中的伪数组(例如通过document.getElementsByTagName获取的元素)具有length属性,并且可以通过0、1、2…下标来访问其中的元素,但是没有Array中的push、pop等方法。我们可以利用call、apply来将其转化为真正的数组这样便可以方便地使用数组方法了。

 
var arrayLike = {

0: 'qianlong',

1: 'ziqi',

2: 'qianduan',

length: 3

}

上面就是一个普通的对象字面量,怎么把它变成一个数组呢?最简单的方法就是

1

var arr = Array.prototype.slice.call(arrayLike);

上面arr便是一个包含arrayLike元素的真正的数组啦( 注意数据结构必须是以数字为下标而且一定要有length属性 )

  • 数组追加

在js中要往数组中添加元素,可以直接用push方法,

 
 
var arr1 = [1,2,3];

var arr2 = [4,5,6];

 

[].push.apply(arr1, arr2);

 

// arr1 [1, 2, 3, 4, 5, 6]

// arr2 [4,5,6]

判断变量类型

对于对象型的数据类型,我们可以借助call来得知他的具体类型,例如数组


function isArray(obj){

return Object.prototype.toString.call(obj) == '[object Array]';

}

 

isArray([]) // true

isArray('qianlong') // false

本文分享自微信公众号 - 大数据钻研(bigdata118)

原文出处及转载信息见文内详细说明,如有侵权,请联系 yunjia_community@tencent.com 删除。

原始发表时间:2016-11-01

本文参与腾讯云自媒体分享计划,欢迎正在阅读的你也加入,一起分享。

我来说两句

0 条评论
登录 后参与评论

相关文章

  • js中call、apply、bind那些事

    前言 回想起之前的一些面试,几乎每次都会问到一个js中关于call、apply、bind的问题,比如… 怎么利用call、apply来求一个数组中最大或者最小值...

    用户1667431
  • 甲骨文在Java问题上不再沉默

    之前有传言称甲骨文要放弃不赚钱的Java,让很多Java开发者内心感到非常不安。 最近有非官方言论说甲骨文公司市场部副总裁对甲骨文Java EE8给出承诺,并承...

    用户1667431
  • 前端开发必备!Emmet使用手册

    介绍 Emmet (前身为 Zen Coding) 是一个能大幅度提高前端开发效率的一个工具: 基本上,大多数的文本编辑器都会允许你存储和重用一些代码块,我们称...

    用户1667431
  • 用故事讲技术:关于js apply、call、bind的区别,我们可以将call忘掉,只使用apply就足够了

    简单说,apply 是给框架设计者用的,而 call 是给开发者用的。两者都能扩充函数作用域。而 bind,主要是绑定作用域,并不是函数执行。

    程序员LIYI
  • js原生函数之call和apply,bind

    call 和 apply 和 bind 都是为了改变某个函数运行时的 context 即上下文而存在的,换句话说,就是为了改变函数体内部 this 的指向。

    用户1394570
  • 机器学习入门 8-7 偏差方差平衡

    本系列是《玩转机器学习教程》一个整理的视频笔记。本小节主要介绍什么是偏差和方差,并从偏差和方差这种更高更全面的视角来探讨模型过拟合和欠拟合,最后提出在算法层面上...

    触摸壹缕阳光
  • 当微信遇上社会工程学,明枪易躲暗箭难防

    帮人开门原本是出于礼节的行为,在当今社会很常见。但在特定场合中,这种行为很可能带来灾难。有些别有用心的人会利用这种礼貌行为,扮成需要帮助的弱者,博取同情,从而顺...

    FB客服
  • 像背单词一样搞定机器学习关键概念:300张小抄表满足你的所有AI好奇

    大数据文摘
  • 一位资深大牛给 Java 初学者的学习建议

    java学习这一部分其实也算是今天的重点,这一部分用来回答很多群里的朋友所问过的问题,那就是我是如何学习Java的,能不能给点建议?今天我是打算来点干货,因此咱...

    程序员宝库
  • 微信回应被下架:将在下个版本中上线暗黑模式

    站长之家(ChinaZ.com) 3月9日 消息:日前,苹果公司发布通知称,要求APP Store商店内应用必须支持iOS13 的夜间模式,否则会面临下架处理。

    数据通20847430

扫码关注云+社区

领取腾讯云代金券