Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

functions extracted from objects unbound by default #13

Open
tvcutsem opened this issue Jul 24, 2012 · 3 comments
Open

functions extracted from objects unbound by default #13

tvcutsem opened this issue Jul 24, 2012 · 3 comments

Comments

@tvcutsem
Copy link

A common mistake in JS is to extract a method from an object (as a first-class function value), then call the function without providing a binding for this. Example:

var obj = {
  offset: 0,
  arr: [1,2,3,4,5],
  nth: function(i) { return this.arr[this.offset + i]; }
};

// incorrect:
var nth = obj.nth;
nth(1); // oops, crashes as `this.offset` is undefined, or in strict-mode because `this` is undefined

// must explicitly bind the function on extraction (easy since ES5):
var nth = obj.nth.bind(obj);
nth(1);

I think the ability to be able to extract methods as unbound functions is useful and powerful (it allows for easy sharing of methods among different objects), but it seems this mistake is so common that extracting methods as bound functions could have been the default.

@michaelficarra
Copy link

@tvcutsem: But how would you unbind a function? Once bound, that function's context becomes useless.

@tvcutsem
Copy link
Author

I wouldn't argue to ever unbind a bound function. Instead, if binding-on-extraction using the dot-operator would have been the default, I would imagine one could still get at the unbound function using reflection, e.g. Object.getOwnPropertyDescriptor(obj, "nth").value. This would make sharing methods between objects more painful though. It all depends on what the more frequent use case of extracting methods is: is the extracted method used as a stand-alone function, or is it installed as a method in another object?

@Ayms
Copy link

Ayms commented Aug 4, 2012

Finally maybe the default behavior is the one that indicates fat arrow :

var obj = {
  offset: 0,
  arr: [1,2,3,4,5],
  nth: (i) => { return this.arr[this.offset + i]; }
};

var nth = obj.nth;

obj.nth(); //|this| is the global or undefined if strict mode
nth(); //idem

Of course, one could have expected the contrary (ie |this| is obj for both)

I did not deeply think about it but doing this project https://github.com/Ayms/node-Tor where the use of "var self=this" is replaced by "bind" (for future replacement by =>) at a certain point of time it came to me the question : "why don't we have an unbind ?", but apparently you are saying that's it's not arguable

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

3 participants