var

var

variable声明一个变量,它任选地初始化为一个值。

语法

var varname1 [= value1] [, varname2 [= value2] ... [, varnameN [= valueN]]];

varnameN变量名。它可以是任何合法的标识符。valueN变量的初始值。它可以是任何法律表达。默认值是未定义的

描述

变量声明,无论它们出现在何处,都会在任何代码执行之前处理。声明的变量的作用域var是当前的执行上下文,它可以是封闭函数,或者对于在任何函数外部声明的变量,全局函数。如果你重新声明一个JavaScript变量,它不会失去它的价值。

赋值给一个未声明的变量隐式地创建它作为一个全局变量(它成为全局对象的一个​​属性),当赋值被执行时。声明变量和未声明变量之间的区别是:

  • 声明的变量在声明它们的执行上下文中受到约束。未声明的变量总是全局性的。

function x() { y = 1; // Throws a ReferenceError in strict mode var z = 2; } x( console.log(y // logs "1" console.log(z // Throws a ReferenceError: z is not defined outside x

2. 声明的变量是在任何代码执行之前创建的。直到分配给它们的代码被执行,未声明的变量才会存在。

console.log(a // Throws a ReferenceError. console.log('still going...' // Never executes.

var a; console.log(a // logs "undefined" or "" depending on browser. console.log('still going...' // logs "still going...".

3. 声明的变量是其执行上下文(函数或全局)的不可配置属性。未声明的变量是可配置的(例如可以被删除)。

var a = 1; b = 2; delete this.a; // Throws a TypeError in strict mode. Fails silently otherwise. delete this.b; console.log(a, b // Throws a ReferenceError. // The 'b' property was deleted and no longer exists.

由于这三个区别,未能声明变量很可能会导致意想不到的结果。因此,建议始终声明变量,而不管它们是处于函数还是全局范围内。在ECMAScript 5严格模式下,分配给未声明的变量会引发错误。

var hoisting

因为在执行任何代码之前处理变量声明(以及通常的声明),所以在代码中的任何位置声明变量相当于将其声明在顶部。这也意味着变量可以在声明之前使用。这种行为称为“提升”,因为看起来变量声明被移到函数或全局代码的顶部。

bla = 2; var bla; // ... // is implicitly understood as: var bla; bla = 2;

因此,建议始终在其作用域顶部(全局代码顶部和功能代码顶部)声明变量,以清楚哪些变量是函数作用域(本地),哪些变量是在作用域链上解析的。

需要指出的是,提升会影响变量声明,但不影响其值的初始化。当达到赋值语句时,该值将分配:

function do_something() {   console.log(bar // undefined   var bar = 111;   console.log(bar // 111 } // is implicitly understood as: function do_something() {   var bar;   console.log(bar // undefined bar = 111;   console.log(bar // 111 }

例子

声明和初始化两个变量

var a = 0, b = 0;

用单个字符串值分配两个变量

var a = 'A'; var b = a; // Equivalent to: var a, b = a = 'A';

请注意顺序:

var x = y, y = 'A'; console.log(x + y // undefinedA

在这里,x并且y在任何代码执行之前声明,分配会在稍后发生。在x = y评估“ ”时,y存在所以不存在ReferenceError,其值为' undefined'。因此,x分配了未定义的值。然后,y分配一个值'A'。因此,在第一行之后x === undefined && y === 'A',因此,得到结果。

初始化几个变量

var x = 0; function f() { var x = y = 1; // x is declared locally. y is not! } f( console.log(x, y // Throws a ReferenceError in strict mode (y is not defined). 0, 1 otherwise. // In non-strict mode: // x is the global one as expected // y leaked outside of the function, though!

隐式全局变量和外部函数范围

似乎是隐式全局变量的变量可能是对外部函数作用域中的变量的引用:

var x = 0; // x is declared global, then assigned a value of 0 console.log(typeof z // undefined, since z doesn't exist yet function a() { // when a is called, var y = 2; // y is declared local to function a, then assigned a value of 2 console.log(x, y // 0 2 function b() { // when b is called x = 3; // assigns 3 to existing global x, doesn't create a new global var y = 4; // assigns 4 to existing outer y, doesn't create a new global var z = 5; // creates a new global variable z and assigns a value of 5. } // (Throws a ReferenceError in strict mode.) b( // calling b creates z as a global variable console.log(x, y, z // 3 4 5 } a( // calling a also calls b console.log(x, z // 3 5 console.log(typeof y // undefined as y is local to function a

规格

SpecificationStatusComment
ECMAScript 1st Edition (ECMA-262)StandardInitial definition. Implemented in JavaScript 1.0
ECMAScript 5.1 (ECMA-262)The definition of 'var statement' in that specification.Standard
ECMAScript 2015 (6th Edition, ECMA-262)The definition of 'variable statement' in that specification.Standard
ECMAScript Latest Draft (ECMA-262)The definition of 'variable statement' in that specification.Draft

浏览器兼容性

FeatureChromeEdgeFirefox (Gecko)Internet ExplorerOperaSafari
Basic support(Yes)(Yes)(Yes)(Yes)(Yes)(Yes)

FeatureAndroidChrome for AndroidEdgeFirefox Mobile (Gecko)IE MobileOpera MobileSafari Mobile
Basic support(Yes)(Yes)(Yes)(Yes)(Yes)(Yes)(Yes)