Understanding the difference between scope and context in a JavaScript method

JavaScript

scope and contextSometimes the concepts of scope and context are misunderstood in JavaScript. It is important to understand that they are not the same thing. This is particularly important inside of a method.

In JavaScript, the concept of scope refers to the visibility of variables. On the other hand, the concept of context is used to mean: “the object to which a method belongs”. That may sound like an odd statement, but it is accurate. The only time we care about context is inside a function. Period. Inside a function, the “this” keyword is very important. It refers to the object to which that function belongs. In other words, every function is a property of some object. In client-side JavaScript (i.e. in a browser), if you declare a function at the top of your code, then that function is a property of the window object. So, inside of that function, the “this” keyword refers to the window object. If you create a new object (let’s call it: “myObject”) and add a method (i.e. a property that happens to be a function), then inside of that function, the “this” keyword refers to the object (i.e. “myObject”).

So the main issue is that inside of a method, object properties and variables can sometimes be confused. In short; when the JavaScript “var” keyword is used, that is a variable. A variable will not be a property of an object (except in the global scope, which is for another discussion). But inside a method, any variable created using the JavaScript “var” keyword will be private to that method. So this means that it is not possible to access that variable from outside the method. But inside of a method, you have access to all of the properties of the object to which that method belongs. And you access these properties using the JavaScript “this” keyword. So, for example; if myObject.greeting = “Hello” and myObject.greet is a method, then inside myObject.greet, if I reference this.greeting, I should get the string: “Hello”. And if I have declared a variable named “speed” inside of myObject.greet, I would access it simply by referring to “speed” (i.e. I would not use the JavaScript “this” keyword). Also, a big difference between variables and properties in a method is that properties are always public. That is to say: all object properties can be seen and in most cases modified. But a private variable inside of a method is completely hidden from the outside world. And only our code inside of the method has access to that variable.

Try it yourself !

In above example, we start out by creating a property on the window object named: “foo”. This “foo” object is the result of an immediately invoked function expression (aka: “IIFE“). The reason that we take this approach is so that we can have a private variable: count. Our getCount method as access to that private count variable.

There is also a count property on the “foo” object. This property is available publicly. That is to say: we are able to make changes to the count property, whereas the count variable is not available outside of the IIFE. Our getCount method has access to the count variable, but that is the only way we can reach it.

When we call foo.getCount() without passing any arguments, then it increments the count property and returns it. This is CONTEXT. By using the JavaScript “this” keyword inside of the getCount method, we are leveraging the concept of context. Conversely, when we call foo.getCount(“scope”), then the count variable is incremented and returned. This is SCOPE. It is very important to understand the difference between scope and context in JavaScript.

Getting Started with ECMAScript 6 Arrow functions – The “this” keyword

JavaScript

ECMAScript 6 LogoOther than syntax, the biggest change that ECMAScript Arrow Functions brings about, is how it relates to context: in the function body, “this” has a different meaning than you may expect.

It seems to me that the two problems that are solved by ECMAScript 6 Arrow functions are: verbose syntax and the tricky nature of “this” inside a function. Granted, when working with methods and constructors, the meaning of “this” is a bit easier to understand. But when working with functions that are not constructors, or not bound to an object, the “this” keyword will resolve to the window object, and that is rarely the behavior you want. In a function that is defined in the global scope, it is probably unlikely that you will intentionally want to refer to “this” (and global function declarations should really be kept to a minimum or even better, avoided at all costs). But when you have a function that is declared inside of a method for example, it is not at all uncommon to attempt access to “this” from the nested function. This is where the frustration starts, because the meaning of “this” will vary depending on the circumstances.

Example # 1A

In Example # 1A, the object foo has two properties: “color”, whose value is: “red”, and the method: “getColor”. The method foo.getColor has a nested function: privateGetColor, which references “this”. The problem is: inside of privateGetColor, “this” refers to the window object. Since there is no window.color, privateGetColor returns: “undefined”, which means that foo.getColor() returns “undefined”.

Example # 1B

In Example # 1B, we have fixed the situation by creating a private variable named: “me” inside of foo.getColor, which caches “this”. This way, the nested function: “privateGetColor” now has access to “this”, and this foo.getColor returns “red”.

Example # 2

In Example # 2, we have a more elegant solution. By leveraging an arrow function, we no longer need to create the variable “me”, in order to cache the value of “this”. Now that the nested function: privateGetColor is an arrow function, we can reference “this” in the arrow function’s body. Since privateGetColor now returns “red”, foo.getColor() returns “red”.

Lexical binding of “this”

The reason that Example # 2 saves the day, is because of the change in meaning for the “this” keyword inside of an arrow function. Normally, “this” will refer to the object of which the function is a method. With arrow functions, “this” is bound lexically. This means that it is where an arrow function is defined that affects the meaning of “this”, not where it is executed.

Example # 3

In Example # 3, we have an object named “bar”, which has a “color” property. When we execute foo.getColor(), we use the call method to change the context in which getColor is executed. This should have changed the meaning of “this” to “bar”, which would result in the return value of “blue (i.e. privateGetColor.call(bar) should return: “blue”). But that is not what happens; the return value of foo.getColor() is: “red”.

The reason for all of this is that inside of an arrow function, “this” is bound lexically. So, it is where an arrow function is DEFINED, not where it is executed, that determines the meaning of “this”. It might help of think of how scope works in JavaScript. The lexical binding of “this” inside the body of an arrow function behaves in a similar way. The closest containing object outside of the arrow function will be resolved as “this”.

Summary

The meaning of “this” inside an arrow function is without doubt a significant change in the JavaScript specification. Since ECMAScript 6 is 100% backwards-compatible, this has no effect on the meaning of “this” inside of normal function definitions, function expressions, constructors or methods. While it may take a while to get used to this concept, the ramifications are very positive. The ability to reference a specific object inside of a click-handler or AJAX calls makes for code that will be easier to read, manage and extend.

The JavaScript “this” Keyword Deep Dive: Nested Functions

JavaScript

JavaScript LogoLearn how the JavaScript “this” keyword behaves inside of function declarations and expressions, even when nested 10 levels deep.

In the article: The JavaScript “this” Keyword Deep Dive: An Overview, we discussed a number of scenarios in which the JavaScript “this” Keyword has different meanings. In this article, we will concentrate on functions and methods.

It’s important to note that methods are functions. What makes a method a method is that the consumer of the code specifies an object, and then calls a method of that object.

Example # 1

In Example # 1, we have executed a function and a method. We have actually executed two functions, but the second function: “someMethod” is actually a method of the “bar” object. We know this because we have used the syntax: object.method().

It’s important to understand the difference between executing a function and a method.

Example # 2

foo = function (){ return this.music; }; console.log(this.music); //’classical’ (global) console.log(foo()); //’classical’ (global)

HERE IS THE JS-FIDDLE.NET LINK FOR EXAMPLE # 2: http://jsfiddle.net/84Yd4/

In Example # 2, we have executed the function “foo”, which returns the value of “this.music”: “classical”. Both console.log statements return the value: “classical”, because since we are not inside of a method, the JavaScript “this” keyword refers to the window object, and at the top of the code, you’ll see that window.music is equal to “classical”.

Example # 3

foo = function (){ function bar(){ function baz(){ function bif(){ return this.music; } return bif(); } return baz(); } return bar(); }; console.log(this.music); //’classical’ (global) console.log(foo()); //’classical’ (global)

HERE IS THE JS-FIDDLE.NET LINK FOR EXAMPLE # 2: http://jsfiddle.net/84Yd4/1/

In Example # 3, things get a bit silly, but the effect is the same. Even inside of nested functions, because none of these functions are methods, the JavaScript “this” keyword refers to the window object. And “this.music” is the same as “window.music”, which is equal to “classical”.

Example # 4

foo = function (){ function bar(){ function baz(){ function bif(){ function billy(){ function bobby(){ function betty(){ function jetty(){ function jimmy(){ function judy(){ return this.music; } return judy(); } return jimmy(); } return jetty(); } return betty(); } return bobby(); } return billy(); } return bif(); } return baz(); } return bar(); }; console.log(this.music); //’classical’ (global) console.log(foo()); //’classical’ (global)

In Example # 4, the function-nesting concept is taken to a ridiculous level. Nonetheless, the output is exactly the same: “this.music” is the same as “window.music”, which is equal to “classical”. It does not matter how deeply a function is nested. Unless it is a method of an object, the JavaScript “this” keyword will always refer to the window object.

HERE IS THE JS-FIDDLE.NET LINK FOR EXAMPLE # 3: http://jsfiddle.net/84Yd4/2/

Summary

In this article we learned that when a function is not specified as a method of an object, the JavaScript “this” keyword refers to the window object. This is true even in the case of nested functions. In fact, no matter how many levels deep we nest functions, the JavaScript “this” keyword refers to the window object.

The JavaScript “this” Keyword Deep Dive: An Overview

JavaScript

JavaScript LogoLearn the subtle yet critical details that allow you to leverage the JavaScript “this” keyword.

In JavaScript, the “this” keyword is one of the most overly-used yet under-utilized aspects of the language. It is also one of the most mis-understood topics. While it facilitates more readable, expressive object-oriented JavaScript, improper use is a catalyst for confusing code that is difficult to debug.

Personally, I’ve struggled to understand the mystery. I’ve heard many unusually long-winded explanations, which I feel only contribute to the silliness. Simply put: In JavaScript, “this” refers to the object upon which a function is invoked. That’s it.

In JavaScript, “this” refers to the object upon which a function is invoked.

This means that “this” can only be used in a function, or globally. When used in either of these cases, “this” refers to the window object. When the function is a method of an object, then “this” refers to the object that the method is a member of. When the function is a constructor, then “this” refers to the instance object. There is much more to talk about with regards to what “this” means in varying scenarios, but these are the most common situations.

Example # 1

In Example # 1, we have added a property to the window object, named it: “music”, and assigned the value “classical”. In the line that follows, we output the value of “this.music”, and the result is: “classical”.

The reason for the output is simple: If you execute arbitrary code in the global context (i.e. outside of a function), then “this” refers to the window object. Executing arbitrary code in the global context is highly discouraged, but it is important to understand this behavior from a theoretical standpoint; in the global context: “this” will evaluate to the window object.

Example # 2

In Example # 2, we have added a function named foo, and then logged the output of that function’s execution. The resulting value is: “classical”. Some may have expected the output to be “blues”. This is a common mistake.

In the function “foo”, “music” is a variable. The “this” keyword has to do with objects, never variables (there is a very subtle scenario where “this” refers to a variable, which we will address in a later post). So the fact that there is a variable named “music” is completely meaningless in this example. The function “foo” does only one thing: it returns the value of this.music. In that function, “this” is the widow object, and the value of window.music is: “classical”. So, the variable “music” is completely ignored.

Example # 3

In Example # 3, we have added an object named “bar”. This object has two properties: “music”, which has a value of “jazz” and “getMusic”: a method that returns the value of bar’s “music” property.

The “getMusic” method has a line of code that you have seen in previous examples: “return this.music”. But why does that line of code return: “jazz”? The reason for this behavior is that when a function is a method of an object, the “this” keyword refers to the object upon which that function is invoked. In this case, the object is “bar”, and bar’s “music” property is equal to “jazz”, so “this.music” is equal to “jazz”.

Example # 4

In Example # 4, we have added the constructor function: “Baz”. “Baz” has a property named “music”, and it is equal to “rock”. It also has a property named “getMusic”, which is a method. The “getMusic” method returns the value of Baz’s “music” property.

You may be thinking that inside of the “Baz” constructor, the “this” keyword refers to the window object, as discussed in Example # 2. If we were to simply execute “Baz” (e.g. Baz() ), then yes, the property window.music would be overwritten and given the value of “rock”, and there would be a new global property named “getMusic”, which would return “rock”.

But that’s not what happens. After we create the constructor: “Baz”, we instantiate it, which results in a variable named “bif”, an instance of “Baz”. When you instantiate a JavaScript constructor function, the “this” keyword inside of that function refers to the instance object that the constructor returns.

HERE IS THE JS-FIDDLE.NET LINK

FOR EXAMPLE # 3:

Summary

In this article we discussed the high-level details of the JavaScript “this” keyword. We learned that it refers to the object upon which a function is invoked, and how it means different things in different scenarios. The scenarios we covered are: the window object, inside of a function, inside of a method, and inside of a constructor function.

Easy JavaScript Object Context Switching with jQuery.proxy()

jQuery

JavaScript LogoA popular saying in the Real Estate business is: “Location, location, location!” Well, in JavaScript, it’s all about “context”. When you want to leverage the very powerful keyword: “this”, then understanding the current context is critical.

So, those experienced with native JavaScript should be comfortable with the concept of context (If you are not, take a moment to brush up on this subject; it’s important.) When you need to specify context, you would normally use the .call() or .apply() methods. The jQuery folks have also provided a way to accomplish this with their .proxy() method. This method takes two arguments, which are: the function to be executed and the object whose context should be targeted. Any additional arguments are optional and are passed to the function that is executed.

Example # 1

In Example # 1, we have created two simple objects: “foo” and “bar”. Note that each object has one property named “music”. Next, we set up two click event handlers. In each case, we execute the “handler” function. And that function makes reference to “this”. If we were to run that function by itself, the output of the alert would be “undefined”, because when doing that, “this” refers to the window object, which at this time has no property named “music”.

So, by using the jQuery.proxy() method, we specify the context within which the “handler” function should be executed.

Here is the JS Fiddle link for Example # 1: http://jsfiddle.net/Shm47/

Example # 2

In Example # 2, we have taken our cause to the DOM. We first create a function named toggleColor, which when passed a class name, will toggle that class name.

Next, we set up two click event handlers. In each case, we leverage jQuery.proxy(), to call the “toggleColor” function, and specify the context within which it should run. We’re also specifying the class name to be passed to that function.

Here is the JS Fiddle link for Example # 2: http://jsfiddle.net/WzDUj/

Summary

In this article, we learned about the jQuery.proxy() method. In doing so, we discussed how it is used to specify the context within which a function should be executed. First we demonstrated how you can leverage this function using object literals. We then showed how you can do so by using DOM elements.

Helpful Links for the jQuery.proxy() method

http://api.jquery.com/jQuery.proxy/
http://stackoverflow.com/questions/3349380/jquery-proxy-usage
http://stackoverflow.com/questions/4986329/understanding-proxy-in-jquery
http://blog.kevinchisholm.com/javascript/context-http://blog.kevinchisholm.com/javascript/difference-between-scope-and-context/object-literals/
http://blog.kevinchisholm.com/javascript/difference-between-scope-and-context/

What is the Difference Between Scope and Context in JavaScript?

JavaScript

scope and contextIn JavaScript, scope and context are not the same thing, and it’s important to understand the difference between them. Fortunately, the answer is short and simple.

Why Should We Care About Scope and Context ?

When interviewing front-end developers, I usually try to include a question about scope and context in JavaScript. I always ask what the difference is, and I am often surprised by the answers I get. It seems that even those with some experience have difficulty answering this question.

The answer is short and simple: Scope pertains to the visibility of variables, and context refers to the object to which a function belongs.

Scope in JavaScript

Scope has to do with the the visibility of variables. In JavaScript, scope is achieved through the use of functions. When you use the keyword “var” inside of a function, the variable that you are initializing is private to the function, and cannot be seen outside of that function. But if there are functions inside of this function, then those “inner” functions can “see” that variable, and that variable is said to be “in-scope”. Functions can “see” variables that are declared inside of them. They can also “see” any that are declared outside of them, but never those declared inside of functions that are nested in that function. This is scope in JavaScript.

Context in JavaScript

Context is related to objects. It refers to the object to which a function belongs. When you use the JavaScript “this” keyword, it refers to the object to which function belongs.

Scope refers to the visibility of variables, and content refers to the object to which a function belongs.

For example, inside of a function, when you say: “this.accoutNumber”, you are referring to the property “accoutNumber”, that belongs to the object to which that function belongs. If the object “foo” has a method called “bar”, when the JavaScript keyword “this” is used inside of “bar”, it refers to “foo”. If the function “bar” were executed in the global scope, then “this” refers to the window object (except in strict mode). It is important to keep in mind that by using the JavaScript call() or apply() methods, you can alter the context within which a function is executed. This, in-turn, changes the meaning of “this” inside of that function when it is executed.

Summary

As a front-end developer, you can surely appreciate what an important topic this is, and how critical it is to understand the difference between scope and context in JavaScript. These two subjects become very important as soon as you have to write or edit even intermediate-level JavaScript, and your ability to comfortably and confidently write / edit JavaScript will only improve once you have a good working knowledge of the difference between scope and context. The good news is, it’s not that difficult to understand and once you get it, you’ve got it.

What’s the Difference Between Scope and Context in JavaScript ? | Skillshare

Understanding Scope in JavaScript – Function Level Scope | Kevin Chisholm – Blog

Understanding Context in JavaScript – Object Literals | Kevin Chisholm – Blog

Understanding Context in JavaScript – Object Literals

JavaScript

JavaScript Logo - context

Why is the word “this” so important in JavaScript?

In the post: “Understanding Scope in JavaScript,” I covered the basics of how scope works when dealing with functions. Sometimes the words “scope” and “context” are used interchangeably, which only leads to confusion because they are not the same thing.

In JavaScript, “context” refers to an object. Within an object, the keyword “this” refers to that object (i.e. “self”), and provides an interface to the properties and methods that are members of that object. When a function is executed, the keyword “this” refers to the object that the function is executed in.

Here are a few scenarios:

So, as you can see, “this” can easily give you a headache. But hang in there; we are getting to the good stuff now.

In a nutshell, in Object-literals, you don’t have local variables; you have properties of the object. So, where inside of the function foo() I might say “var drink = ‘beer’; “, for an object literal called “bar”, I would say “bar.dink = ‘beer’. “ The difference is that “beer” is a property of “bar”, whereas when a function is executing, a local variable is defined by the “var” keyword and cannot be seen by anyone or anything outside of the function.

Example # 1

Here is the jsFiddle.net link for Example # 1: http://jsfiddle.net/Q9RJv/

In Example # 1, we first create a global variable named “drink”, and set it equal to “wine”. We’ll come back to that in a minute.

Next, we create an Object Literal named “foo”, with a property “drink” that is equal to “beer”. There is also a method that simply returns “drink”. But why does it return “wine”, and not “beer”? This is because in the object “foo”, “drink” is a property of foo, not a variable. Inside of functions, when reference is made to a variable, the JavaScript engine searches the scope chain and returns the first match it finds.

Although this function executes in the context of “foo”, “foo” does not have a variable named “drink”. It has a property named “drink”, but not a variable. So the JavaScript engine searches the next level of the scope chain. The next level of the scope chain is the global object, which contains a variable named “drink”, so the value of that variable (“wine”), is returned.

But wait a minute Kevin, how can we make reference to the property “drink” that is in the context of the object “foo”?

I’m glad you asked.

Example # 2

Here is the jsFiddle.net link for Example # 2: http://jsfiddle.net/HGM93/

In Example # 2, the only change we have made is that in the anonymous function that is assigned to “getDrink”, we return “this.drink” instead of “drink

This is an important detail. When a function executes in the context of an object , the keyword “this” refers to that object. You can access any of the properties of the object by using the “this” keyword, add new ones (e.g. this.color = “blue”), and change existing ones (e.g. this.drink = “juice).

Using Dot Notation to Create a JavaScript Object Literal

Example # 3

Here is the jsFiddle.net link for Example # 3: http://jsfiddle.net/ZA77k/

In Example # 3, we have the exact same functionality as Example # 2. From the JavaScript engine’s perspective, we have achieved the same goal, and the console output is exactly the same.

The difference is how we organized our code. In Example # 2, we created the properties “drink” and “getDrink” at the exact same time that we created the object literal “foo”. It is all one expression. In Example # 3, we create an empty object named “foo” first, and then use dot notation to add properties to the object one-by-one. I just wanted to point out that there is more than one way to go about all of this from a syntax perspective.

Object Literals Can Contain Other Object Literals, and those Objects Have Their Own Context

Example # 4

Here is the jsFiddle.net link for Example # 4: http://jsfiddle.net/8p38y/

In Example # 4, we have added a new property to “foo”, and that property is yet another object. At first it is empty (i.e. foo.under21 = {}), and then we add two properties to it. The first property is “drink”, which is set equal to “soda”. Don’t’ confuse this with the property “drink” that is set in the context of “foo” which is equal to “beer”. In the context of “foo.under21”, “drink” is equal to “soda”.

The second property of “foo.under21” has an anonymous function assigned to it. That anonymous function returns “this.drink”. In the context of “foo.under21”, “drink” is equal to “soda”, so calling that function returns “soda”.

So the point of this example is that object literals can have properties that are themselves objects, and those objects have their own context. When functions execute in the context of those objects “this” refers to the object, and so on. I am aware of no limit to this kind of object nesting.

The JavaScript .call() and .apply() Methods Allow You to Dynamically Change the Context In Which a Function is Executed

Example # 5

Here is the jsFiddle.net link for Example # 5: http://jsfiddle.net/A5ydt/

Ok, so here is the bonus question: In Example # 5, why does a call to “foo.under21.getDrink()” now return “wine” ?

This is because we changed the inner-workings of that function. Instead of simply returning “this.drink”, we use the JavaScript “.call()” method, which allows you to execute any function in the context of another object. When you do not specify the context in which that function is to be “called”, it executes in the context of the global object. In the global context, there is a variable named “drink” and it is equal to “wine”, so “wine” is returned.

Example # 6:

Here is the jsFiddle.net link for Example # 6: http://jsfiddle.net/cS4cv/

In Example # 6, “soda” is returned because when we used the JavaScript “.call()” method, we specified the context in which the function is to execute. In this case, the context we specify is “this”. “this” refers to the context of “foo.under21”, and “foo.under21” has a property named “drink”, so the value “soda” is returned.

Summary

The last two examples may seem like overkill, but I wanted to point out that just when you start to get a handle on the concept of context in JavaScript object literals, you must realize that there is a bit more to consider. JavaScript Object Literals can have properties that are also objects, and those objects have their own context.

In each case, when a function executes within that context, inside of the function, the “this” keyword refers to the object that the function is a property of, because the function executes in the context of that object. By using the JavaScript “.call()” method (or “.apply()” method), you can programmatically change the context in which that function executes, which changes the meaning of the “this” accordingly.