What Does 'This' Mean in JavaScript? The Keyword Explained
Tags: javascript, webdev, programming, productivity
Published: 2022-09-22 21:03:27

While working with JavaScript, you’ll inevitably come across the `this` keyword. As a concept, it can be quite tricky to grasp! Normally `this` refers to the object that **owns** the method. However, its meaning is entirely different — depending on how the function is called.

In this article, we’ll be looking at `this` in detail.

## Background
Objects are the basic building blocks of JavaScript! _And the `this` keyword will **always** refer to an object_. You can check its current value at every line of code execution. **The value of `this` is determined based on the code’s **execution context**.**

### Execution Context
JavaScript code is read and executed line by line. The environment (or scope), of the line currently being executed, is known as **Execution Context**.

Behind the scenes, JavaScript runtime is maintaining a stack of these execution contexts and the context present at the top of this stack — is the one currently being executed.

The object that `this` refers to changes every time the execution context is changed.

This is why `this` can be difficult to understand! Let’s look at `this` in a number of different contexts — so we can learn how it works!

## “this” in Global Scope
If there is no current object, `this` refers to the global object. Within our browser that happens to be the `window` object. It’s the top-level object which represents the document.

Let’s test to confirm:
```js
function testThis() { 
   console.log(this === window); 
} 

testThis(); 
// returns true

console.log(this === window) 
// returns true
```

## “this” when calling Function
The value of `this` remains as the global object if you’re calling a function:
```js
window.check = "Hi! I'm the window object";

function thisFunction() {
	alert(this.check); // Hi! I'm the window object
	alert(window === this); // true
}

thisFunction();
```

### “this” in Methods
When we call a function as a method of an object, `this` refers to the object, which is then known as the receiver of the function call.

In the following example, the method `quote` is inside an object called `author`. The `quotes‘` `this` value refers to `author` itself. So the `author` object will receive the `quote` method call:
```js
const author = {
  name: "Oscar Wilde",
  quote() {
    console.log(`Be yourself. Everyone else is already taken. - ${this.name}`);
  }
};
author.quote();
```

## “this” with call() and apply()
A function’s `this` value is set implicitly, however, we can also call a function with an explicit `this` argument with `call()` and `apply()`.

Essentially, `call()` and `apply()` run JavaScript functions as if they were methods of another object.

Let’s see an example:
```js
function testThis(type) {
   this.test = "I'm the "+type+"!";
}

let firstObject = {};
testThis.call(firstObject, "firstObject");

console.log(firstObject.test); 
// I'm the firstObject

let secondObject = {};
testThis.apply(secondObject, ["secondObject"]);

console.log(secondObject.test); 
// I'm the secondObject
```
The only difference is that `call()` expects a discrete number of parameters while `apply()` can be passed an array of parameters.

Note: If you’re using `call` or `apply` outside of **strict mode**, then passing `null` or `undefined` using `call` or `apply` will be ignored by the JavaScript engine. This is one of the reasons why it is usually suggested to always write code in strict mode!

## “this” with bind()
The `bind()` method allows us to **permanently** tie a `this` argument to a value. So in the below example, `bind` will create a new `quote` function and set its `this` value to `author`.
```js
const author = {
  name: "Oscar Wilde",
  quote() {
    console.log(`Be yourself. Everyone else is already taken. - ${this.name}`);
  }
};
setTimeOut(author.quote.bind(author), 1000);
```
By doing so, our `this` cannot be changed with the `call` or `apply` methods.

## “this” inside an Arrow Function
Using `this` with an arrow function is different from any other kind of JavaScript function. _An arrow function uses the `this` value from its enclosing execution context since it does have one of its own_.

An arrow function permanently captures the `this` value, preventing `apply` or `call` from being able to change it later on.

For example:
```js
const author = this;

const oscarWilde = () => {
  console.log(this === oscarWilde);
};

oscarWilde();
// false
```
Here, we are storing the value of a `this` in a variable and then comparing the value with a `this` value that is inside an arrow function.

An arrow function’s `this` value **cannot** be set explicitly! Also, the arrow function will ignore any attempt to pass a value to `this` using methods like `call`, `apply`, and `bind`. An arrow function will refer to the `this` value that was set when the arrow function was created.

_Note_: An arrow function can also not be used as a constructor. So we cannot assign properties to `this` inside an arrow function.

## Summary
So now, you can figure out the value of `this` with these simple rules:

- By default, `this` refers to global object — within the browser, this is the `window` object.
- When a method is called as a property of object, `this` refers to the parent object.
- When a function is called with a `new` operator, `this` refers to the newly created instance.
- When a function is called using `call()` and `apply()`, then `this` refers to the value passed as the first argument of the method.

## Conclusion
We’ve looked at how `this` works in a number of different contexts, such as global scope, functions, methods, `call()`, `apply()`, `bind()`, and arrow functions!

If you liked this blog post, follow me on [Twitter](https://twitter.com/RembertDesigns) where I post daily about Tech related things!
![Buy Me A Coffee](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/ijinng8k7bf23v0o6gkj.png) If you enjoyed this article & would like to leave a tip — click [here](https://www.buymeacoffee.com/rembertdesigns)

### 🌎 Let's Connect

- [Portfolio](https://www.rembertdesigns.co/)

- [Twitter](https://twitter.com/RembertDesigns)

- [LinkedIn](https://www.linkedin.com/in/rrembert/)

- [Hashnode](https://rembertdesigns.hashnode.dev/)

- [Devto](https://dev.to/rembertdesigns)

- [Medium](https://medium.com/@rembertdesigns)

- [Github](https://github.com/rembertdesigns)

- [Codepen](https://codepen.io/rembertdesigns)