What is “this” in Javascript?

What is “this” in Javascript – especially, when you use bind( ), arrow function and regular function?

  this refers to its closest object.


Maya, you’re not making any sense!

Wait, let me explain. 


If this is called in a global scope, then this refers to “window” object in a browser or “global” object in Node.

function checkThis() {
  return this;
}

// In a browser:
checkThis() === window; // true 

// In Node:
checkThis() === global; // true

But what other things that could be inside this ?

The answer is, well … whatever the object is.

this is but an alias to the actual object. See below, this is equivalent to user.

let user = {
  name: "Maya",
  age: 30,

  callMe() {
    alert(this.name);
    alert(user.name);
  }

};

user.callMe(); // will output "Maya", and then "Maya" again

That’s it?

Wait, there is more! 

this is defined or evaluated during run-time. The moment you create or write this, this is just a concept or a keyword in the ocean of your codebase (that you expect to work and mean something, of course). But only when the function runs, this will turn into an object (or undefined, when there is no object in its outer scope and when the code is set to be in a strict mode).

let human = { name: "Maya" };
let dog = { name: "Pillow" };

function sayHi() {
  alert( this.name );
}

// register the function in two objects
human.sayHi = sayHi;
dog.sayHi = sayHi;

When we call sayHi() on two different objects (human and dog), this is a different object each time.

this inside the following function is the object “before the dot”

human.sayHi(); // Maya  (this == human)

this inside the following function call is defined “before the opening bracket”

dog['sayHi'](); // Pillow  (this == dog)

*Both function call styles work just the same.

So the meaning of this relies on the scope, its closest object and the run-time of our function then?

Not necessarily. Especially if that is not what you want.


We can actually decide what this should be!

How?

We can tie our this to whatever object we pass in to our bind().

Let’s see two examples of similar code with different names addThis() and noThis(), both run console.log(this);

function addThis() {
  console.log(this) // 'this' = "hello" because it is bound to "hello"
}


function noThis() {
  console.log(this); // 'this' = window object
}

let runMe = addThis.bind("hello"); // ties "hello" to addThis

runMe(); // executes addThis and returns "hello" 

noThis(); // executes noThis and returns a window object 

Metaphorically, bind() is like the matchmaker that sets up your girl friend (the this) with a guy (the Object). We use bind’s matchmaking service, so she (this) will not end up with some random guys (the window guys, the global guys, the undefined guys – because heaven forbid; or some other guys who are not good for her (wrong objects that wreak havoc the code).

But what about a function that lives inside a function that is already bound to an object?

Will that inner function inherit the bound object of its parent’s function?

The answers are : YES AND NO.

Yes, if the inner function is an arrow function.

Because this type of function does not have its own this, but will latch on to any object that its parent is bound to (a Window object if the arrow lives in the global scope).

No, if the inner function is a function that uses function keyword.

Because, this type of function, will lose its binding / object context and back to refer to the window object again.

function parentFunc() {
  console.log(this) // 'this' = "hello"
  
  childFuncArrow = () => { 
     console.log(this); // 'this' = "hello"
  };

  childFuncArrow();

   
  function childFuncNormal() {
     console.log(this); // 'this' = the window object - oh no!
  }

  childFuncNormal();
  
}

let runMe = parentFunc.bind("hello"); 

runMe(); // execute parentFunc which outputs "hello", "hello", window object

Even if we don’t use bind(), inner arrow function will always take its this from the nearest object – which in this case is bound to the arrow function by its normal function parent, the twoFunctions(). But inner normal function will lose its context.

The example below, shows an arrow function’s this as the human object (its direct parent’s this) and the normal function will return undefined.

let human = {

  name: "Maya",
  
  twoFunctions() {

    console.log(this.name); //  output "Maya"

    let arrow = () => console.log(this.name); // output "Maya"

    arrow();
    
    function notArrow() {
      console.log(this.name); // output "undefined" - because it tries to call window.name
    }
 
    notArrow();
  },
}
  
human.twoFunctions(); // Will output "Maya" and "undefined"

4 Comments

  1. Jgsvjarly January 1, 2021 at 6:14 am

    viagra online mastercard wildviagra generic viagra soft tabs

  2. naim izle January 19, 2021 at 10:49 am

    Respect to post author, some wonderful information . Agnesse Harcourt Haney

  3. free porn January 21, 2021 at 2:28 pm

    Appreciate it for helping out, great information. Tove Waldemar Rainer

Leave a comment

Your email address will not be published. Required fields are marked *