I have below class, but I'm confused by the bind this here. The class don't have a constructor and super(), why did he need to do bind this on setAll method? I removed the bind this, the application still work and no error.
class PushScheduleActions {
/**
* Request all API
*/
fetchAll(params) {
return dispatch => {
dispatch(params);
PushScheduleApi.getAll(params)
.then(this.setAll.bind(this));//why use bind this here?
.catch(this.setError.bind(this));
}
}
setAll(data) {
return data;
}
}
There is no relation between constructor, super and bind.
What bind does?
it returns a new function with the context user passed.
In your case, PushScheduleApi success case you are passing a new setAll function which is returned by bind method.
since your setAll function doesn't use context, you don't need to pass the context.
dispatch is an arrow function, so context is inherited. So you dont need bind method. you can simply use this.setAll
The class don't have a constructor and super()
That's completely irrelevant.
why did he need to do bind this on setAll method?
The method only needs to be bound if
it uses thisand
this should refer to what this refers to inside fetchAll (likely an instance of PushScheduleActions).
Since setAll doesn't reference this, there is no reason to bind.
However, the whole setAll method is unnecessary. The code would work exactly the same without .then(this.setAll.bind(this)). That makes me think that PushScheduleActions is supposed to be subclassed and child classes are supposed to overwrite setAll. Now, the child class' setAll might use this and expect it to refer to the instance. Since the parent class (PushScheduleActions) can't know that, binding the method is safer since it will ensure that child class implementations of setAll will work regardless if they use this or not.
The bind() function creates a new bound function (BF). A BF is an exotic function object (a term from ECMAScript 2015) that wraps the original function object. Calling a BF generally, results in the execution of its wrapped function.
For more detail follow this link i hope it will help you a lot to understand to bind() method
Use of the JavaScript 'bind' method
Related
I have read lot of theory regarding call(), apply() and bind().
I am not able to understand if we can call method directly why we need call() , apply() or bind()?
Can somebody explain in laymen terms and little in terms of JavaScript?
That's the flexibility offered by Javascript, an object and it's method don't have to be coupled with each other.
Given following object 'a' with a member method 'play'
var a = { play: function (content) { console.log("what is this:", this, content)} }
Use
a.play('Hello')
Is equivalent to
a.play.call(a, 'Hello')
As for your question why need the second way 'call'. Because 'call' gives you a way to call something else instead of 'this', which is 'a' in the example above, so you can do:
a.play.call(document, 'Hello')
About 'apply', it's just another version of 'call', which needs you to pass arguments as an array instead of comma separated parameters. To use apply, you do:
a.play.apply(a, ['Hello'])
As for 'bind', it is to link a function with a 'this' object at first, then get a returned callable object, which you can either call with the rest arguments directly, or pass it into anything else to be called later.
A typical 'bind' use case is React component's event handler. To define an event handler to be passed into a component. You need to use 'bind' in a React class component like this:
handleClick = this.handleClick.bind(this)
Then, in render function:
<Button onClick={this.handleClick} />
Check https://reactjs.org/docs/handling-events.html for the full information.
How to Get context of a decorated function?
I use TypeScript as a transpiler. The sample is complicated because in my case it is an inversifyjs container and a decorator applied to a method. Locator calls the method and applies the context and arguments. The new decorated function is called. I need to call the real method. The problem is that I can not find it. Target variable does not point to the actual context. And context in descriptor.value is shown as undefined. This variable is undefined. Is it impossible in JavaScript?
reference code segment
this.localizationChanged = this.localizationChanged.bind(this);
Who can tell me why to write like that?
Who can tell me why to write like that?
localizationChanged is used as event handler:
LocalizationStore.addChangeListener(this.localizationChanged);`
If the handler was not bound to the component instance, this would not refer to the component instance and it wouldn't be possible to call the setState method of the component (this.setState(...)).
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.
from MDN.
If you are trying to access this in localizationChanged function you bind this.
However in ES2015 you don't require this.You can use arrow operator :
localizationChanged =()=>{
console.log(this);
}
I'm reading someone's code and I see the following:
this.device_name.changes().onValue(this.changeName.bind(this))
From what I understand, onValue takes a callback function, and that function is this.changeName.bind(this)). Correct me if I'm wrong:
The default value of this in a function call refers the object with which the function was called upon.
The .bind(someObject) method causes the function's this to refer to someObject instead, when the function gets executed.
Knowing this (heh), this.changeName.bind(this) seems redundant: the default value for this when calling this.changeName will be the same this that is passed in the bind parameter.
So! Can the function be safely refactored to simply this.changeName with no differences in behavior?
No, the bind is very important here.
A function's this pointer is set at the time the function is called. The call, in this case, is down inside whatever object is invoking the callback. Many objects just call with a this pointer either as null or (in the case of DOM objects) pointing to the DOM object itself.
Using the bind function this way returns a new function that hard-wired the this reference to the value passed to bind. If you take out the bind, it'll completely hose up the this pointer. It will DEFINITELY change the behavior.
Does anybody know? Couldn't find this question asked before, even though it seems fairly basic.
The context (the this keyword) it's not completely implicit, it can be set and changed explicitly.
For example:
function test () {
alert(this);
}
test.call("Hello world");
The test function is called with a string as the context.
So in conclusion, you cannot know what this is unless you explicitly define it, or you are inside the function.
The same function will see different values of this depending on how it called. See Crockford for details, but there are four cases:
Invoked as a simple function, it is bound to the global/window object.
Invoked as a method on an object, it refers to that object.
Invoked as a constructor via the new keyword, it is the newly instantiated object, which inherits from the object stored in function's own prototype property.
Invoked by its own apply or call method, it is the first argument supplied.
If these cases sound complex, tedious, and error-prone, all the more reason to avoid relying on this outside of methods, where it makes the most sense anyway.