this keyword in JavaScript — Details understanding

Iqbal M Ipel
5 min readNov 30, 2018

--

In this article, we will discuss the keyword “this” in JS. It’s really important to understand how “this” works here in JS since “this” has a very high impact in OO world. As we already know JS is a full-fledged functional programming language and along with that, you can achieve almost everything which you need to achieve to implement OO strategies. This capability makes JS one of the most popular programming paradigm now, most importantly industry is using JS heavily nowadays.

“this” keyword contributes a lot to make JS OO paradigm.

What is this?

It’s a reserved keyword in JS programming paradigm. Whoever (developers) comes from a typical OOP world, please don’t think, it works the same way it is in java/.net. Unfortunately/fortunately, it’s not. “this” exactly means the same thing the way it does in English it doesn’t mean anything without the context. Before having a deep dive into “this”, its highly required to understand the execution context of JS.

Execution Context of JS:

There is no compilation step in code execution in JS, interpreter starts reading the code from the top and executes line by line. The environment or scope in which the line is being executed is known as execution context and the execution context present at the top of this stack is currently being executed.

An execution context is an abstract concept of an environment where the JS code is executed. Whenever any code is run in JavaScript, it runs inside an execution context.

The object that “this” refers changes every time execution context is changed.

· Global Execution Context -Default: window or node.

· Functional Execution Context — Every time a function is invoked, a brand new execution context is created for that function. Each function has its own execution context, but it’s created when the function is invoked or called.

How “this” works :

When “this” refers global context:

By default, the execution context for an execution is global which means that if a code is being executed as part of a simple function call then “this” refers to a global object.

o In the Browser, it is a window.

o In node env, it is global.

Let's see which value is assigned to “this” keyword :

Normal Functions Call :

function getGlobalWindowForThis(){
console.log('A simple function : Excution contaxt');
console.log('Value of this keyword :', this);//prints window
console.log(this === window); // prints true
}
getGlobalWindowForThis();Output : A simple function : Excution contaxt
Value of this keyword : window
True

Normal Functions Call with Strict mode:

If strict mode is on, The value of this(global context) will be undefined.

function getGlobalWindowForThis(){
'use strict';
console.log('A simple function : Excution contaxt');
console.log('Value of this keyword :', this); //prints undefined
console.log(this === window); // false
}
getGlobalWindowForThis();Output :A simple function : Excution contaxt
Value of this keyword : undefined
false

Immediately Invoked Function Expression (IIFE)

(function getGlobalWindowForThis(){
console.log('A simple function : Excution contaxt');
console.log('Value of this keyword :', this); //prints window
console.log(this === window); // true
})();
Output :A simple function : Excution contaxt
Value of this keyword : window
True

When Create an object using Object literal :

Whenever fullName() method is called thru person object(person.fullName()), the execution context has been changed global context to functional context. Therefore, in the functional context, the value of the “this” refers to the scope obj, which is the person here.

However, The last method calls(fName();) prints undefined, because the value of fName is a method name. Whenever a method(fName()) is being called, the execution context is global, so the value of “this” is undefined.

FYI, a function can be assigned to a variable as a value like integer, string etc.

let person = {
firstName : 'Iqbal',
lastName : 'Ipel',
fullName : function(){
console.log('FullName :'+this.firstName + ' ' + this.lastName)
}
}
person.fullName(); // Prints Iqbal IpelOutput :
FullName : Iqbal Ipel
let fName = person.fullName
fName(); // undefined.

To fix above undefined problem whenever a function is being called as variable, we need to bind the obj along with the function.

let fName = person.fullName.bind(person);
fName(); // Iqbal Ipel
Output :
FullName : Iqbal Ipel

“this” refers to invoker object (parent object)

As I mentioned earlier, a property of an object can be a function or a variable. In below case, the value of conFly is a function name fly.

When an Object’s method is invoked then “this” refers to the object which contains the method being invoked. bird.canFly(), when canFly is invoked thru bird object, this refers to the bird object as this parent object.

let goAway = bird.isFly; goAway(); when goAway is being called, the Execution Context is global (explained above).

function fly(){
console.log('The value of this:',this) // Print the bird
console.log('Yes!!! I can fly');
console.log(this === window);
}
let bird = {
name : 'Crew',
canFly : fly,
isFly : function(){
console.log('The value of this:',this) // Print the bird
console.log('Yes!!! I can fly too');
console.log(this === window);
}
}
bird.canFly();// FalseOutput (goAway()):
The value of this: { name: 'Crew',
canFly: [Function: fly],
isFly: [Function: isFly]

}
Yes!!! I can fly
False
let goAway = bird.isFly;
goAway(); // True
Output (goAway()):
The value of this: window
Yes!!! I can fly
True.
bird.isFly() // FalseOutput (bird.isFly()):
The value of this: { name: 'Crew',
canFly: [Function: fly],
isFly: [Function: isFly]
}
Yes!!! I can fly
False

With above example, it is clear that how the value of “this” can be confusing in some cases. The function definition of isFly is same but when it is being called as a simple function call then “this” refers to global object and when same definition is invoked as an object’s method then this refers to the parent object. So the value of “this” depends on how a method is being invoked as well.

When Create an object using New keyword:

In below case, When a function is getting called using new then this function called as a constructor, the constructor creates a new object and assigns this to the “this”.

In case of myName.fullName(), “this” refers to new instance myName and in case of myBroName.fullName();, “this” refers to myBroName which is a different instance of myName.

function Name(fn,ln){
this.firstName = fn,
this.lastName = ln,
console.log(this) // Print the Name
this.fullName = function(){
console.log(`Full Name: ${this.firstName} ${this.lastName}`);
}
}
let myName = new Name("Iqbal", "Ipel");
myName.fullName(); // Prints Iqbal Ipel
let myBroName = new Name("Ifty", "Nopel");
myBroName.fullName(); // Prints Ifty Nopel
Output:The value of this: Name { firstName: 'Iqbal', lastName: 'Ipel' }
Full Name: Iqbal Ipel
The value of this: Name { firstName: 'Ifty', lastName: 'Nopel' }
Full Name: Ifty Nopel

Summary

In nutshell,

  • By default, “this” refers to the global object(Window: browser, global: nodejs)
  • When a method is called thru(using dot notation) object, then “this” refers to the calling object.
  • When a function is called with “new” operator then “this” refers to the newly created instance.
  • bind is used to bind the obj with functional context.

One more critical is undergoing on More example of “this” and bind along with call and apply method is in on the way.

Ref :

--

--