- The old «var»
- “var” has no block scope
- “var” tolerates redeclarations
- “var” variables can be declared below their use
- IIFE
- Summary
- Comments
- JavaScript Variables
- Example
- Note
- Example using var
- Note
- Example using let
- Example using const
- Mixed Example
- When to Use var, let, or const?
- Just Like Algebra
- Note
- JavaScript Identifiers
- Note
- The Assignment Operator
- Note
- JavaScript Data Types
- Example
- Declaring a JavaScript Variable
- Example
- Note
- One Statement, Many Variables
- Example
- Example
- Value = undefined
- Example
- Re-Declaring JavaScript Variables
- Example
- Note
- JavaScript Arithmetic
- Example
The old «var»
The information in this article is useful for understanding old scripts.
That’s not how we write new code.
In the very first chapter about variables, we mentioned three ways of variable declaration:
The var declaration is similar to let . Most of the time we can replace let by var or vice-versa and expect things to work:
var message = "Hi"; alert(message); // Hi
But internally var is a very different beast, that originates from very old times. It’s generally not used in modern scripts, but still lurks in the old ones.
If you don’t plan on meeting such scripts you may even skip this chapter or postpone it.
On the other hand, it’s important to understand differences when migrating old scripts from var to let , to avoid odd errors.
“var” has no block scope
Variables, declared with var , are either function-scoped or global-scoped. They are visible through blocks.
if (true) < var test = true; // use "var" instead of "let" >alert(test); // true, the variable lives after if
As var ignores code blocks, we’ve got a global variable test .
If we used let test instead of var test , then the variable would only be visible inside if :
if (true) < let test = true; // use "let" >alert(test); // ReferenceError: test is not defined
The same thing for loops: var cannot be block- or loop-local:
for (var i = 0; i < 10; i++) < var one = 1; // . >alert(i); // 10, "i" is visible after loop, it's a global variable alert(one); // 1, "one" is visible after loop, it's a global variable
If a code block is inside a function, then var becomes a function-level variable:
function sayHi() < if (true) < var phrase = "Hello"; >alert(phrase); // works > sayHi(); alert(phrase); // ReferenceError: phrase is not defined
As we can see, var pierces through if , for or other code blocks. That’s because a long time ago in JavaScript, blocks had no Lexical Environments, and var is a remnant of that.
“var” tolerates redeclarations
If we declare the same variable with let twice in the same scope, that’s an error:
let user; let user; // SyntaxError: 'user' has already been declared
With var , we can redeclare a variable any number of times. If we use var with an already-declared variable, it’s just ignored:
var user = "Pete"; var user = "John"; // this "var" does nothing (already declared) // . it doesn't trigger an error alert(user); // John
“var” variables can be declared below their use
var declarations are processed when the function starts (or script starts for globals).
In other words, var variables are defined from the beginning of the function, no matter where the definition is (assuming that the definition is not in the nested function).
…Is technically the same as this (moved var phrase above):
…Or even as this (remember, code blocks are ignored):
function sayHi() < phrase = "Hello"; // (*) if (false) < var phrase; >alert(phrase); > sayHi();
People also call such behavior “hoisting” (raising), because all var are “hoisted” (raised) to the top of the function.
So in the example above, if (false) branch never executes, but that doesn’t matter. The var inside it is processed in the beginning of the function, so at the moment of (*) the variable exists.
Declarations are hoisted, but assignments are not.
That’s best demonstrated with an example:
The line var phrase = «Hello» has two actions in it:
The declaration is processed at the start of function execution (“hoisted”), but the assignment always works at the place where it appears. So the code works essentially like this:
Because all var declarations are processed at the function start, we can reference them at any place. But variables are undefined until the assignments.
In both examples above, alert runs without an error, because the variable phrase exists. But its value is not yet assigned, so it shows undefined .
IIFE
In the past, as there was only var , and it has no block-level visibility, programmers invented a way to emulate it. What they did was called “immediately-invoked function expressions” (abbreviated as IIFE).
That’s not something we should use nowadays, but you can find them in old scripts.
Here, a Function Expression is created and immediately called. So the code executes right away and has its own private variables.
The Function Expression is wrapped with parenthesis (function <. >) , because when JavaScript engine encounters «function» in the main code, it understands it as the start of a Function Declaration. But a Function Declaration must have a name, so this kind of code will give an error:
// Tries to declare and immediately call a function function() < // ();
Even if we say: “okay, let’s add a name”, that won’t work, as JavaScript does not allow Function Declarations to be called immediately:
// syntax error because of parentheses below function go() < >(); //
So, the parentheses around the function is a trick to show JavaScript that the function is created in the context of another expression, and hence it’s a Function Expression: it needs no name and can be called immediately.
There exist other ways besides parentheses to tell JavaScript that we mean a Function Expression:
// Ways to create IIFE (function() < alert("Parentheses around the function"); >)(); (function() < alert("Parentheses around the whole thing"); >()); !function() < alert("Bitwise NOT operator starts the expression"); >(); +function() < alert("Unary plus starts the expression"); >();
In all the above cases we declare a Function Expression and run it immediately. Let’s note again: nowadays there’s no reason to write such code.
Summary
There are two main differences of var compared to let/const :
- var variables have no block scope, their visibility is scoped to current function, or global, if declared outside function.
- var declarations are processed at function start (script start for globals).
There’s one more very minor difference related to the global object, that we’ll cover in the next chapter.
These differences make var worse than let most of the time. Block-level variables is such a great thing. That’s why let was introduced in the standard long ago, and is now a major way (along with const ) to declare a variable.
Comments
- If you have suggestions what to improve - please submit a GitHub issue or a pull request instead of commenting.
- If you can't understand something in the article – please elaborate.
- To insert few words of code, use the tag, for several lines – wrap them in tag, for more than 10 lines – use a sandbox (plnkr, jsbin, codepen…)
JavaScript Variables
In this first example, x , y , and z are undeclared variables.
They are automatically declared when first used:
Example
Note
It is considered good programming practice to always declare variables before use.
From the examples you can guess:
Example using var
Note
The var keyword was used in all JavaScript code from 1995 to 2015.
The let and const keywords were added to JavaScript in 2015.
The var keyword should only be used in code written for older browsers.
Example using let
Example using const
Mixed Example
The two variables price1 and price2 are declared with the const keyword.
These are constant values and cannot be changed.
The variable total is declared with the let keyword.
The value total can be changed.
When to Use var, let, or const?
1. Always declare variables
2. Always use const if the value should not be changed
3. Always use const if the type should not be changed (Arrays and Objects)
4. Only use let if you can't use const
5. Only use var if you MUST support old browsers.
Just Like Algebra
Just like in algebra, variables hold values:
Just like in algebra, variables are used in expressions:
From the example above, you can guess that the total is calculated to be 11.
Note
Variables are containers for storing values.
JavaScript Identifiers
All JavaScript variables must be identified with unique names.
These unique names are called identifiers.
Identifiers can be short names (like x and y) or more descriptive names (age, sum, totalVolume).
The general rules for constructing names for variables (unique identifiers) are:
- Names can contain letters, digits, underscores, and dollar signs.
- Names must begin with a letter.
- Names can also begin with $ and _ (but we will not use it in this tutorial).
- Names are case sensitive (y and Y are different variables).
- Reserved words (like JavaScript keywords) cannot be used as names.
Note
JavaScript identifiers are case-sensitive.
The Assignment Operator
In JavaScript, the equal sign ( = ) is an "assignment" operator, not an "equal to" operator.
This is different from algebra. The following does not make sense in algebra:
In JavaScript, however, it makes perfect sense: it assigns the value of x + 5 to x.
(It calculates the value of x + 5 and puts the result into x. The value of x is incremented by 5.)
Note
The "equal to" operator is written like == in JavaScript.
JavaScript Data Types
JavaScript variables can hold numbers like 100 and text values like "John Doe".
In programming, text values are called text strings.
JavaScript can handle many types of data, but for now, just think of numbers and strings.
Strings are written inside double or single quotes. Numbers are written without quotes.
If you put a number in quotes, it will be treated as a text string.
Example
Declaring a JavaScript Variable
Creating a variable in JavaScript is called "declaring" a variable.
You declare a JavaScript variable with the var or the let keyword:
After the declaration, the variable has no value (technically it is undefined ).
To assign a value to the variable, use the equal sign:
You can also assign a value to the variable when you declare it:
In the example below, we create a variable called carName and assign the value "Volvo" to it.
Then we "output" the value inside an HTML paragraph with >
Example
let carName = "Volvo";
document.getElementById("demo").innerHTML = carName;
Note
It's a good programming practice to declare all variables at the beginning of a script.
One Statement, Many Variables
You can declare many variables in one statement.
Start the statement with let and separate the variables by comma:
Example
A declaration can span multiple lines:
Example
Value = undefined
In computer programs, variables are often declared without a value. The value can be something that has to be calculated, or something that will be provided later, like user input.
A variable declared without a value will have the value undefined .
The variable carName will have the value undefined after the execution of this statement:
Example
Re-Declaring JavaScript Variables
If you re-declare a JavaScript variable declared with var , it will not lose its value.
The variable carName will still have the value "Volvo" after the execution of these statements:
Example
Note
You cannot re-declare a variable declared with let or const .
JavaScript Arithmetic
As with algebra, you can do arithmetic with JavaScript variables, using operators like = and + :
Example
You can also add strings, but strings will be concatenated: