call,apply,bind三种区别?

257 阅读1分钟

[相同点]

都是天生自带的方法(Function.prototye),所有的函数都可以调取这三个方法 改变this指向

[区别]

  • call传参-散列式(一个个的)
  • apply传参-打包式(把所有的参数放到数组中)
  • bind传参-和call一样

call

  • fn.call(context,para1,para2....)
  • 把fn方法执行,并且让fn方法中的this变为context,而para1...都是给fn传递的实参
//=> 非严格模式
function fn(num1,num2){
    console.log(this);
}
var obj={fn:fn};
obj.fn(); //this:obj

var opp={};
//opp.fn(); //报错:opp中没有fn属性
fn.call(opp); //this:opp  num1,num2 都是undefined
fn.call(1,2); //this:1   num1=2 num2=undefined
fn.call(opp,1,2); //this:opp num=1,num2=2

//=>call的特殊性
fn.call(); //this: window
fn.call(null);//this:window
fn.call(undefined); //this:window
//=>严格模式
"use strict"
fn.call(); //this:undefined
fn.call(undefined); //this:undefined
fn.call(null); //this:null

apply

apply的语法和call基本一致,作用原理也基本一致,唯一的区别:apply把传递给函数的实参以数组的形式存放(但是也相当于给函数一个个的传递实参值)

fn.call(null,10,20,30);
fn.apply(null,[10,20,30])

bind(预处理机制)

  • 它在IE6-8下不兼容;它和call(以及apply)改变this原理不一样
  • 把所有的参数传给点前面的方法,返回一个接收参数后的小函数(返回值是函数的定义)
  • 预处理机制:提前把所有的事情都处理好,最终函数执行需要手动运行
function fn(n,m){
    console.log(this+n+m)
}
var res = fn.bind({},3,5)
res(); //[object Object]35

补充:

  • call继承:只继承了父类的私有方法
  • 利用apply的机制,求数组中的最大值
let max = Math.max.apply(Math,ary),
    min = Math.min.apply(Math,ary);
console.log(max, min);