如果let
关键字引入了块范围的正确实现,那么var
是否还有一个用例?我从软件设计的角度来看这个,而不是语法,“你可以”的立场。
答案 0 :(得分:13)
如果
let
关键字引入了块范围的正确实现,那么var
是否会有用例?
可能有一个用例:全局范围内的let
声明不会在全局对象上创建属性。例如:
"use strict"; // for chrome
var foo = 42;
let bar = 21;
console.log('window.foo (var)', window.foo); // 42
console.log('window.bar (let)', window.bar); // undefined
来自8.1.1.4 Global Environment Records
全局环境记录的对象Environment Record组件包含所有内置全局变量(clause 18)的绑定以及 FunctionDeclaration ,引入的所有绑定全局代码中包含的GeneratorDeclaration 或 VariableStatement 。全局代码中所有其他ECMAScript声明的绑定包含在全局环境记录的声明性环境记录组件中。
但是,通过直接分配给全局对象创建显式全局变量,也可以轻松解决这个问题:
window.foo = 42;
这也是创建全局类btw的唯一方法,因为class
声明具有相同的行为。
(注意:我不主张使用全局变量)
有一些语法结构只能使用var
,但这更多是规范演变的结果,并没有真正用于任何实际目的。例如:
if (true)
var foo = 42; // valid but kind of useless or bad design
// vs
if (true)
let foo = 42; // invalid
块范围不是唯一有用的功能。 temporal dead zone是另一个更容易找到错误的便利功能。比较:
var foo = 42;
function bar() {
console.log(foo); // undefined
var foo = 21;
}
bar();
// vs
var foo = 42; // or `let`, doesn't matter
function bar() {
console.log(foo); // ReferenceError, temporal dead zone
let foo = 21;
}
bar();
尝试访问尚未初始化的let
变量时出现引用错误。
答案 1 :(得分:4)
let
无法在全球范围 中使用。 var
可以。
这是您在严格模式之外尝试全局let
时从Chrome获得的内容:
在严格模式之外尚不支持块范围的声明(let,const,function,class)
答案 2 :(得分:2)
Practically there are some use-cases I found for myself.
Sometimes you may want to declare variable in try-catch like so:
try {
//inits/checks code etc
let id = getId(obj);
var result = getResult(id);
} catch (e) {
handleException(e);
}
//use `result`
With let
the result
declaration would be before try
, which is a bit early and out of context for the author and a reader of the code.
Same is for conditional declarations:
if (opts.re) {
var re = new RegExp(opts.re);
var result = match(re);
if (!result) return false;
}
//use result here safely
With let
this code would be a bit forced to complain "good style", though that might be impractical.
Also I can imagine the case where you would like to use variables belonging to the loop block:
for (var x = 0; x < data.width; x++) {
if (data[x] == null) break;
//some drawing/other code
}
//here we have the `x` pointing to the end of data
Someone with high beauty standards may consider that untidy, I myself prefer let
s, but if the code I edit already contains var
s - that is natural to use them and makes coding easier.
答案 3 :(得分:0)
如果要在函数范围内解构某些内容,可以使用var
,例如,有条件的:
if (Math.random() > 0.5)
var {a,b} = {a: 1, b: 2}
else
var {a,b} = {a: 10, b: 20}
// Some common logic on a and b
console.log(a, b)
使用let
,您将必须编写类似
let result;
if (Math.random() > 0.5)
result = {a: 'foo', b: 'bar'}
else
result = {a: 'baz', b: 'qux'}
// Using const might make more sense here
let {a, b} = result;
// Some common logic on a and b
console.log(a,b)