我对这条线感到困惑:
> return fToBind.apply(this instanceof fNOP
> ? this
> : oThis,
> aArgs.concat(Array.prototype.slice.call(arguments)));
在mdn site的polyfill for bind中,我认为我发现了一个错误,但它可能被安全功能所掩盖,以防止参数数组被泄露。下面的三元运算符错误地将函数参数与提供的函数参数连接起来,然后再次将函数参数连接起来并将其传递给函数。但是在函数中,显示的唯一参数是正确的值。调用函数时它们去了哪里。使用测试代码1,2,3调用该函数证明了oThis被用作这个并且1,2,3而不是1,2,3,1,2,3被打印出来。为什么呢?
另外,为什么逗号运算符不会跳过oThis
并仅评估参数项。我认为它会跳过oThis因为逗号运算符,并且作为从第二个到最后一个连接到所有参数的参数进行求值。
if (!Function.prototype.bind2) {
Function.prototype.bind2 = 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
? this
: oThis,
aArgs.concat(Array.prototype.slice.call(arguments)));
};
console.log("is the ternary returned?"+ !(this instanceof fNOP));
console.log("aArgs: " + aArgs + " slice: " +
`${aArgs.concat(Array.prototype.slice.call(arguments))}`);
//true, aArgs: 1,2,3 slice: 1,2,3,[object Object],1,2,3
if (this.prototype) {
// Function.prototype doesn't have a prototype property
fNOP.prototype = this.prototype;
}
fBound.prototype = new fNOP();
return fBound;
};
}
//Test outputs: this!=global: true args: 1,2,3
(function(){console.log(`this!=global: ${this!=self} args:
${Array.from(arguments)}`);}.bind2({t:"s"},1,2,3))();

答案 0 :(得分:1)
下面的三元运算符错误地将函数参数与提供的函数参数连接,然后再次将函数参数连接起来
没有。三元与连接无关。
为什么逗号运算符不会跳过oThis并仅评估参数项。
没有逗号运算符。有一个逗号分隔传递给apply
调用的两个参数。三元表达式是第一个参数,数组连接是第二个参数。
fToBind.apply(
this instanceof fNOP ? this : oThis
,
aArgs.concat(Array.prototype.slice.call(arguments))
);
你可以删除concat,它仍然有用
没有。尝试一个实际将参数传递给绑定函数的示例:
(function() {
console.log(`this: ${this}, args: ${Array.from(arguments)}`);
}).bind2("thisValue", 1,2,3)(4,5,6);
我对
console.log("slice: "+…)
的输出感到困惑。争论的额外点在哪里?
那是因为你确实把console.log
放在了错误的地方。它不在fBound
函数中,因此您看到的arguments
对象是.bind2
调用的对象。