If I declared a variable at the top of a Javascript file like:
let x = 3;
How can I change it in a function later? I know you can use window.x with variables set by var, but how do you change it if it was declared by let?
let x = 3;
function myFunction(){
x = 4;
};
You have set a global variable x. It is available globally. Your function changes that global variable to 4. Simple as that.
let x = 3;
function myFunction(){
x = 4;
};
console.log(x) // 4
To perhaps expand on this, what if you were to re-declare x inside myFunction()? That would shadow the global x you declared at the top. Global x would still be 3 even after you ran the code, but x would be 4 inside the function.
let x = 3;
function myFunction(){
let x = 4; // this will now shadow the global x at the top
console.log(x);
};
console.log(x) // 3
And if you were to run myFunction()...
myFunction(); // 4
Related
This question already has answers here:
What does var mean in Javascript? [closed]
(2 answers)
Closed 3 years ago.
I can't understand why the x after test won't become 30 but still remains 10
<script>
function test(){
var x = 30;
y = 40;
}
</script>
<script>
var x = 10;
var y = 20;
document.write("before test, x: " + x + ", y: " + y + "<br/><br/>");
test();
document.write("after test, x: " + x + ", y: " + y + "<br/><br/>");
</script>
This is because by declaring var x = 30;, you create a variable named x that exists only in the function's scope.
The variable y, however, is only defined at top-level. So when you run the function test, you edit the local x variable, and the global (top-level) y variable.
When you define variables they are hoisted at top of its scope. Let me show you how your current code:
function test(){
var x = 30;
y = 40;
}
var x = 10;
var y = 20;
test();
Will run like this:
// global scope
var x; // x is undefined
var y; // y is undefined
function test() {
// function scope
var x; // x is undefined inside this scope
x = 30; // x is assigned with value 30
y = 40; // y is assigned with value 40
// the global scope y value is assigned
}
x = 10; // x is assigned with value 10
// the global scope x value is assigned
y = 20; // y is assigned with value 20
// the global scope y value is assigned
test();
// when calling test,
// you see x is assigned with its function scope
// and y is assigned with its global scope
// so, at this point
// x becomes 10
// y becomes 40
You can read more about var here in the docs. Also, look in the scope, global scope and local scope.
Also, note that let and const works differently. They are scoped in the block. You can read them in the corresponding links which are linked here in.
This is a thought exercise. I'm not doing anything with this code and the purpose is to better understand how closures work.
Thought Process:
x === 10 in global scope.
outer() function is called.
x === 20 in the global scope and local scope.
inner() function is called.
right side of 'var x' is expressed.
In x + 20, because x is not defined in local scope, it searches outer scope and finds x === 20.
var x = 20 + 20.
var x === 40.
return x.
result === 40.
However, the answer is 20. Why is this?
var x = 10;
function outer () {
x = 20;
function inner () {
var x = x + 20;
return x;
}
inner();
}
outer();
var result = x;
When the inner() function is called, the first thing that happens is var x.
This means the JavaScript interpreter first creates a variable named x to which it assigns undefined.
Then it runs the assignment expression x + 20, which is equivalent to undefined + 20 which is NaN.
Your variable result has nothing to do with your inner() function as you have a local variable (because of that var x) and you ignore the returned result.
In other words, your code is equivalent to just this:
var x = 10;
function outer () {
x = 20;
}
outer();
var result = x;
Because your inner function defined a local var x which will hide the global variable outside. And the outer function uses the global variable x and assign it to 20. Obviously, the global x is 20. Javascript will define every local variable before you call the function in the prototype chain.
var x = 10;
function outer () {
x = 20;
function inner () {
alert(x); // alert undefined
var x = x + 20;
return x;
}
inner();
}
outer();
var result = x;
Why does z() execution context not override global x variable?
var x = 10;
function z(){
var x = x = 20;
}
z();
console.log(x); // why is 10 printed? Shouldn’t it be 20.
var a = b = c = 0;
It means b and c are being declared as globals, not locals as intended.
For example -
var y = 10;
function z(){
var x = y = 20; // global y is overridden
}
z();
console.log(y); // value is 20
Going by above logic, x = x = 20 in z() means x is global which overrides the local x variable but still global value of x is 10
The internal x declaration is hoisted to the top of the function, and overshadows the x of the external scope. Your code actually does this:
var x = 10;
function z(){
var x;
x = x = 20;
}
z();
console.log(x); // why is 10 printed? Shouldn’t it be 20.
Why does z() execution context not override global x variable?
var x = 10;
function z(){
var x = x = 20;
}
z();
console.log(x); // Why is 10 printed? Shouldn’t it be 20.
var a = b = c = 0;
It means b and c are being declared as globals, not locals as intended.
For example:
var y = 10;
function z(){
var x = y = 20; // Global y is overridden.
}
z();
console.log(y); // Value is 20.
Going by above logic, x = x = 20 in z() means x is global which overrides the local x variable but still global value of x is 10.
function z(){
var x = x = 20;
}
Due to hoisting, this effectively gets turned into:
function z(){
var x;
x = x = 20;
}
So every instance of x in that function is referring to the local variable, not the global variable.
var x = x = 20;
is interpreted as
var x;
x = (x = 20);
so global x is not pointed.
var x = 10;
function z(){
var x = x = 20;
}
z();
console.log(x)
The local first x. The second x will not be hoisted because we already have x hoisted. So the x will be 20 locally but 10 as global.
For
var y = 10;
function z(){
var x = y = 20; // global y is overridden
}
z();
console.log(y); // value is 20
The x will be hoisted locally but the y will not hoist locally because it is not declared so it will leak to the global scope which is assigned 10. The global scope got changed locally to become 20. So that is why you are getting 10.
Why the y is leaked outside the function as scope in JavaScript are bound to functions.
A detailed explanation would be fruitful.
var x = 0;
function f(){
var x = y = 1; // x is declared locally. y is not!
};
f();
console.log(x, y); // 0, 1
It's just syntax error.
The line var x = y = 1; Means:
Declare local variable x,
y = 1,
Declare global variable y (since it's not declared)
x = y;
Replace
var x = y = 1;
with
var x = 1, y = 1;
or
var x = 1;
var y = 1;
and you will get local variable y
http://www.w3schools.com/js/js_variables.asp
The reason the y variable is global is that in Javascript if you omit the var keyword from an assignment statement, the variable the value is assigned to is declared on the global object.
That means that if you wrote the f() function this way, declaring both x and y with the var keyword:
function f(){
var x, y;
x = y = 1;
};
Then both x and y would be local variables (local x shadowing the global one).
It's bad practice to assign a variable without declaring it (with the var keyword).
New versions of JS will throw an error on this. You can use EC5's strict mode to take advantage of this behavior:
https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Functions_and_function_scope/Strict_mode
so you'd write your function this way:
function f(){
'use strict'
var x, y;
x = y = 1;
};
now if you forget to declare y you get an error yelling at you to do so.