JavaScript中的call、apply、bind用法

这三种都是用来明确指定 this 关键字所指对象到底是谁。

Function.prototype.call()

call() 方法调用一个函数, 其具有一个指定的this值和分别地提供的参数(参数的列表)。

语法 fun.call(thisArg, arg1, arg2, ...)

thisArg:在fun函数运行时指定的this值。
需要注意的是,指定的this值并不一定是该函数执行时真正的this值,如果这个函数处于非严格模式下,则指定为null和undefined的this值会自动指向全局对象(浏览器中就是window对象),同时值为原始值(数字,字符串,布尔值)的this会指向该原始值的自动包装对象。

arg1, arg2, ...:指定的参数列表。

例子:

function greet() {
  var reply = this.person + ' Is An Awesome ' + this.role
  console.log(reply);
}

var i = {
  person: 'Romeo', 
  role: 'Javascript Developer'
};

greet.call(i); // Romeo Is An Awesome Javascript Developer

Function.prototype.apply()

apply() 方法调用一个具有给定this值的函数,以及作为一个数组(或类似数组对象)提供的参数。
注意:call()方法的作用和 apply() 方法类似,区别就是call()方法接受的是参数列表,而apply()方法接受的是一个参数数组。

语法 func.apply(thisArg, [argsArray])

thisArg 可选的,在 func 函数运行时使用的 this值。
请注意,this可能不是该方法看到的实际值:如果这个函数处于非严格模式下,则指定为 nullundefined 时会自动替换为指向全局对象,原始值会被包装。

argsArray 可选的,一个数组或者类数组对象,其中的数组元素将作为单独的参数传给func函数。还可以使用数组字面量(array literal),例如fun.apply(this, [0,1,2])
如果该参数的值为 nullundefined,则表示不需要传入任何参数。从ECMAScript 5 开始可以使用类数组对象。

例子:

var numbers = [5, 6, 2, 3, 7];
var max = Math.max.apply(null, numbers);
console.log(max);
// expected output: 7

var array = ['a', 'b'];
var elements = [0, 1, 2];
array.push.apply(array, elements);
console.info(array); // ["a", "b", 0, 1, 2]

Function.prototype.bind()

bind()方法创建一个新的函数, 当这个新函数被调用时this键值为其提供的值,其参数列表前几项值为创建时指定的参数序列。

语法 fun.bind(thisArg[, arg1[, arg2[, ...]]])

thisArg
调用绑定函数时作为this参数传递给目标函数的值。 如果使用new运算符构造绑定函数,则忽略该值。当使用bind在setTimeout中创建一个函数(作为回调提供)时,作为thisArg传递的任何原始值都将转换为object。如果没有提供绑定的参数,则执行作用域的this被视为新函数的thisArg
arg1, arg2, ...
当绑定函数被调用时,这些参数将置于实参之前传递给被绑定的方法。

例子:
创建一个函数,无论怎么调用都有同样的this

this.x = 9; 
var module = {
  x: 81,
  getX: function() { return this.x; }
};

module.getX(); // 返回 81

var retrieveX = module.getX;
retrieveX(); // 返回 9, 在这种情况下,"this"指向全局作用域

// 创建一个新函数,将"this"绑定到module对象
// 新手可能会被全局的x变量和module里的属性x所迷惑
var boundGetX = retrieveX.bind(module);
boundGetX(); // 返回 81

猜你喜欢

转载自blog.csdn.net/romeo12334/article/details/84636430