In simple terms, this is a special keyword in JavaScript that refers to the current object or execution context in which a function is being called.
In JavaScript, the behavior of this is one of the most difficult concepts to understand because it is somewhat different from most languages.
The important thing is that this always refers to the execution context of the function. This execution context can be:
- The global context when calling a function from outside an object.
- The object that calls a method from within the object.
- A specific object that we explicitly “force” (using methods
call(),apply(), orbind()).
Let’s look at each one in detail 👇
Behavior of ‘this’
In JavaScript, the value of this depends on how the function is called, not on how it is defined.
In regular functions
When a function is invoked in a simple manner (without using objects or special methods), this refers to the global context.
function greet() {
console.log(this); // `this` refers to the global object
console.log("Hello!");
}
greet();
In this case, when saludar() is executed, the value of this is the global object. (window in a browser or global in Node.js)
In strict mode ("use strict";), this does not refer to the global object, but will be undefined.
From object methods
When a function is invoked as a method of an object, the value of this refers to the object to which the method belongs.
const person = {
name: "Luis",
greet: function() {
console.log(this.name); // `this` refers to the `person` object
}
};
person.greet(); // Output: "Luis"
In this case, when persona.saludar() is invoked, this refers to the persona object, which allows access to the nombre property within the method.
Losing the ‘this’ object
One of the biggest headaches with this is that it’s easy to “lose” the reference to the object we intended.
When we define a function inside a method, if we’re not careful, this might refer to the global object instead of the expected object.
const person = {
name: "Luis",
greet: function() {
function innerGreet() {
console.log(this.name); // `this` refers to the global object
}
innerGreet();
}
};
person.greet(); // Error: `this.name` is `undefined`, since `this` is the global object
In this example,
- Inside
saludar(), we define the functionsaludarInterno(). - However,
thisinsaludarInterno()does not refer topersona, but to the global context. - This can cause the
nombreproperty to not be accessible correctly.
‘this’ in arrow functions
Arrow functions in JavaScript have special behavior regarding this.
Instead of setting their own this value, arrow functions inherit the value of this from the lexical context in which they were defined.
const person = {
name: "Luis",
greet: function() {
const sayHello = () => {
console.log("Hello, I am " + this.name); // `this` refers to `person`
};
sayHello();
}
};
person.greet(); // "Hello, I am Luis"
In this case,
personais an object with a propertynombreand a methodsaludar.- Inside the
saludarmethod, we define an arrow function calleddecirHola. - The arrow function inherits the
thiscontext from thesaludarmethod, which points to thepersonaobject. - When calling
decirHola, it uses the “correct” value ofthisand accesses persona.nombre.
Explicitly modifying
In JavaScript, we can explicitly modify the value of this using the methods call(), apply(), and bind().
These methods allow us to set the execution context for a function, regardless of how it is invoked.
Summary of everything we’ve seen:
- In regular functions,
thisrefers to the global context. - In object methods,
thisrefers to the object containing the method. - In functions inside methods, care must be taken, as
thiscan change depending on the context of the inner function. - Arrow functions do not have their own
this, but inherit thethisfrom their lexical context. - call(), apply() and bind() allow explicitly changing the value of
thiswhen invoking a function.
