非常有趣。你为什么这么想?
var fn1 = function() {
function fn2() {
return "fn2 initialize...."
}
if (false) {
function fn2() {
return "fn2 if --> false"
}
}
return fn2();
}
fn1(); // "fn2 if --> false"
或更有趣;
var fn1 = function() {
function fn2() {
return "fn2 initialize...."
}
if (false) {
function fn2() {
return "fn2 if --> false"
}
}
return fn2();
function fn2() {
return "fn2 return after"
}
}
fn1(); // "fn2 return after"
答案 0 :(得分:10)
该代码中发生了两件事,其中一件是指定的行为,另一件在语法上无效(现在),其结果因JavaScript引擎而异。
无效位是条件块中不能有函数声明。例如,这个位无效:
if (false) {
function fn2() {
return "fn2 if --> false"
}
}
某些引擎会将其视为函数声明,这意味着它不受逐步代码流的影响(因为函数声明不是,它们在步骤之前发生 - 步骤流程。)
其他引擎将(实际上)重写为您的函数表达式,将其置于逐步流程中。
我相信ECMAScript6将解决这个问题。
指定的位涉及在同一范围内只有两个声明,例如:
var fn1 = function() {
function fn2() {
return "the first fn2"
}
return fn2();
function fn2() {
return "the second fn2"
}
};
fn1(); // "the second fn2"
规范明确指出范围内的所有函数声明都按源顺序处理,因此上面(删除了无效位)可靠地使用第二个fn2
,不是第一个。