The MDN bind polyfill is shown below.
I am trying to work out the purpose of
this instanceof fNOP ? this : oThis
in the fToBind.apply
invocation.
I can't get my head around it. Can someone help shed some light?
Function.prototype.bindMdn = 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)));
}
;
if (this.prototype) {
// Function.prototype doesn't have a prototype property
fNOP.prototype = this.prototype;
}
fBound.prototype = new fNOP();
return fBound;
};
It seems to be a short-circuit if an instance of the bound function is supplied as the target when invoking the bound function, but the typeof check should catch this, so I don't understand its presence.
Link to the MDN page:
https://developer.mozilla.org/en/docs/Web/JavaScript/Reference/Global_objects/Function/bind
Edit: This is a different question from the suggested duplicate. The suggested duplicate asks why fNOP
is needed. I fully grok that.
This question is why the instanceof
check is needed and what function it serves. I present my short-circuit hypothesis above, together with a reason why that doesn't fully make sense.
Polyfill is a browser fallback. If your browser don't have the bind() and you have to write your own bind() function, that is what we are going to do here. So, let's impolement our own bind() function. Let's have a look of actual bind(): let name={ fN:'Shubham', lN:'Verma' } let printN=function(){ console.
We use the Bind() method to call a function with the this value, this keyword refers to the same object which is currently selected . In other words, bind() method allows us to easily set which object will be bound by the this keyword when a function or method is invoked.
The bind() method creates a new function that, when called, has its this keyword set to the provided value, with a given sequence of arguments preceding any provided when the new function is called.
Call invokes the function and allows you to pass in arguments one by one. Apply invokes the function and allows you to pass in arguments as an array. Bind returns a new function, allowing you to pass in a this array and any number of arguments.
If you use the result of a .bind
to create a new instance with new
:
function TestClass(a,b,c,d) {
}
var TestClassBound = TestClass.bindMdn(null, 1, 2, 3);
new TestClassBound();
Then this instanceof fNOP
is true
.
The typeof this !== 'function'
is just there to test if it was called a regular way on a function and not with call
or apply
or to make sure it was not copied to another objects prototype. So it only prevent something like
Function.prototype.bind.call("Not a function", 1, 2, 3);
Or
var testObj = {};
testObj.bind = Function.prototype.bind;
testObj.bind(1,2,3);
For every regular call of bind
on a function the typeof this
will always be function
.
So the typeof this !== 'function'
is to check if the object bind
is called is really a function.
And the this instanceof fNOP
within the fBind
ensures that the behaviour is correct when the result of the binding is used.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With