了解javascript借用方法

时间:2016-07-07 13:06:42

标签: javascript

关于如何将函数的arguments转换为真实数组有很多解释。

但是当我在bind的帮助下简化代码时,我发现它非常有趣。

MDN Array.prototype.slice - Array-like objects

MDN Function.prototype.bind - Creating shortcuts

例如:

function list() {
  return Array.prototype.slice.call(arguments);
}

var list1 = list(1, 2, 3); // [1, 2, 3]

简化通话:

var unboundSlice = Array.prototype.slice;
var slice = Function.prototype.call.bind(unboundSlice);

function list() {
  return slice(arguments);
}

var list1 = list(1, 2, 3); // [1, 2, 3]

如果您使用apply代替call

,它的工作方式相同
var slice = Function.prototype.apply.bind(unboundSlice);

甚至可以通过在任何函数实例中使用call来缩短它,因为它与原型中的{1}和来自数组实例的slice的方法相同:

var slice = alert.call.bind([].slice);

你可以尝试

var slice = alert.call.bind([].slice);

function list() {
    console.log(slice(arguments));
}

list(1, 2, 3, 4);

因此,我想到的第一个非常奇怪的事情是在bind上调用apply,但bind的第一个参数应该是一个对象(作为上下文)而不是一个函数(Array.prototype.slice)。

另一个是以同样的方式使用callapply

我正在写javascript很长一段时间并且日复一日地使用这些方法,但我无法解决这个问题。

也许我错过了一些非常基本的细节。

有人可以解释一下吗?

2 个答案:

答案 0 :(得分:2)

  

bind的第一个参数应该是一个对象(作为上下文)

  

而不是函数(Array.prototype.slice)。

为什么不呢?首先,所有函数都是对象,所以没有错。

从另一个角度来看,如果您使用slice.call(…)slice.apply(…),则slice对象 call /的上下文(接收方) apply方法调用。

  

绑定applycall之间的区别是什么?

applyBoundToSlice(arguments)callBoundToSlice(arguments)之间没有区别。如果您希望将applyBoundToSlice(arguments, [0, n])传递给开始和结束参数,则差异为callBoundToSlice(arguments, 0, n)slice

答案 1 :(得分:0)

一个人可以使用call关键字来实现方法借用。下面的示例显示了方法借用。

var john = {
  name: "John",
  age: 30,
  isAdult: function() {
    console.log(this.name+"'s age is "+this.age);
    if (this.age > 18) {
      return true;
    } else {
      return false;
    }
  }
}

console.log(john.isAdult());

var rita = {
  name: "Rita",
  age: 15
}

console.log(john.isAdult.call(rita));

观察最后一行。关键字调用的用法以及rita对象如何传递给函数。