Jonathan Ong
Jonathan Ong

Reputation: 20315

`this` inside a function that isn't a prototype of a class

I'm trying to make a class without prototypes. Here is an example:

test = (function() {
  this.value = 1;
  this.print = function() {
    console.log(this.value);
  };
  return this;
})();

This works perfectly as intended. What I don't understand is this.value inside the this.print function. How does this.print correctly know that any mention of this refers to test and not window? Would any function defined via this.___ = function(){} automatically have this added as a context?

Upvotes: 4

Views: 103

Answers (1)

user166390
user166390

Reputation:

this always1 evaluates to the object upon which the function-object was invoked. It will evaluate to window if it was "invoked upon nothing" (or is a property of window).

(Note that this is not a variable and is thus not closed-over in a closure! This is why sometimes closures are needed to get the "correct" this which is often known by the variable self or that or _this.)

For example:

function f () { return this; }
var a = {f: f}
var b = {f: f}
a.f() === a     // true
b.f() === b     // true
f() === window  // true

An example of using a variable to create a binding to the current (as of when the enclosing function was invoked) this:

test = (function() {
  var self = this // <-- variable, which is "closed over"
  this.value = 1; // self === this
  this.print = function() {
    console.log(self.value); // <-- self "names" previous this object
  };
  return this;
})();

1 This is a little lie. The Function.call and Function.apply functions allow specifying the this context and can be used by "context binding" functions such as Function.bind to eliminate the need for an explicit "self closure" as shown above.

Upvotes: 11

Related Questions