在javascript里面没有块级作用域,都是通过函数来限制的,变量在函数内部以var开头声明为函数的局部变量,如果没有关键字var 则变量为全局变量,全局变量作为window对象的属性存在的,在函数内部的局部变量只能在函数内部访问,函数内部可以访问其上一级的变量,如果内部和上一级的变量/函数重名,则内部变量/函数覆盖外部变量/函数
示例代码如下
var name = "外部的变量"; function showName () { var name = "内部的变量"; // 局部变量 console.log (name); // Jack } console.log (name); //结果:外部的变量
没有块级作用域
var name = "Richard"; if (name) { name = "Jack"; // this name is the global name variable and it is being changed to "Jack" here console.log (name); // Jack: still the global variable } // Here, the name variable is the same global name variable, but it was changed in the if statement console.log (name); // Jack
切记一定要在使用变量之前声明变量,局部变量优先于全局变量
var name = "Paul"; function users () { // Here, the name variable is local and it takes precedence over the same name variable in the global scope var name = "Jack"; // The search for name starts right here inside the function before it attempts to look outside the function in the global scope console.log (name); } users (); // Jack
在setTimeout 执行的函数、单独函数,闭包、中this指向window。即使用this获取的变量为全局变量
// The use of the "this" object inside the setTimeout function refers to the Window object, not to myObj var highValue = 200; var constantVal = 2; var myObj = { highValue: 20, constantVal: 5, calculateIt: function () { setTimeout (function () { console.log(this.constantVal * this.highValue); }, 2000); } } // 这里面的this指向的全局对象,并不是我们期待的myObj
// because the reference to "this" in the setTimeout function refers to the global window object, not to the myObj object as we might expect. myObj.calculateIt(); // 400
为了避免污染全局作用域,尽量少使用全局变量。
所有变量如果再函数内部声明会被提升的函数的顶部,如果再函数外部声明会被提升到当前上下文的顶部,只要在变量声明的时候才会提升,而不是在初始化的时候。
如果变量声明与函数名字相同(不分声明先后),函数声明优先于变量声明(不是变量赋值)。如果变量声明的时候并且进行了初始化,则函数被覆盖
function showName () { console.log ("First Name: " + name); var name = "Ford"; console.log ("Last Name: " + name); } showName (); // First Name: undefined // Last Name: Ford // The reason undefined prints first is because the local variable name was hoisted to the top of the function // Which means it is this local variable that get calls the first time. // This is how the code is actually processed by the JavaScript engine: function showName () { var name; // name is hoisted (note that is undefined at this point, since the assignment happens below) console.log ("First Name: " + name); // First Name: undefined name = "Ford"; // name is assigned a value // now name is Ford console.log ("Last Name: " + name); // Last Name: Ford }
// 只声明外部变量为myName,同时定义名字同样为myName的函数 var myName; function myName () { console.log ("Rich"); } // 函数声明覆盖变量声明 console.log(typeof myName); //function
// 变量的声明初始化会覆盖后面的函数 这个时候函数定义无效 var myName = "Richard"; // This is the variable assignment (initialization) that overrides the function declaration. function myName () { console.log ("Rich"); } console.log(typeof myName); // string
请注意如下方式,如果函数为表达式方式,则函数会覆盖变量
var myName = "Richard"; var myName = function () { console.log ("Rich"); } console.log(typeof myName);//function