Javascript 如果在上限范围中声明变量,并且在未执行的语句中在本地范围中声明具有相同名称的变量,则该变量在本地范围中未定义

Javascript 如果在上限范围中声明变量,并且在未执行的语句中在本地范围中声明具有相同名称的变量,则该变量在本地范围中未定义,javascript,Javascript,警报1 function a(){ var h = 1; function b(){ alert(h); } b(); } a(); 警报未定义。为什么?函数作用域中的变量在整个函数的作用域中。var是否在块内并不重要。因此: function a(){ var h = 1; function b(){ if(false){ var h = h * 2; }

警报1

function a(){
    var h = 1;
    function b(){
        alert(h);
    }
    b();
}
a();

警报未定义。为什么?

函数作用域中的变量在整个函数的作用域中。
var
是否在块内并不重要。因此:

function a(){
    var h = 1;
    function b(){
        if(false){
            var h = h * 2;
        }
        alert(h);
    }
    b();
}
a();
相当于:

function b(){
    if(false){
        var h = h * 2;
    }
    alert(h);
}

周围函数也有一个名为
h

的变量并不重要。变量声明被移动到定义它们的范围的顶部,并且在执行赋值行之前,不会赋值。因此,您的第二个代码可以理解为

function b(){
    var h;
    if(false){
        h = h * 2;
    }
    alert(h);
}

尽管在
if
子句中定义了
h
,但由于JavaScript没有块作用域,变量声明实际上被移动到函数的顶部。而且由于
如果
条件不满足,
h
永远不会被赋值。这就是为什么它会提醒
未定义

您正在使用'var'声明'h'。删除'var'的第二个实例,如下所示:

function a() {
    var h = 1;

    function b() {
        var h;
        if (false) {
            h = h * 2;
        }
        alert(h);
    }
    b();
}
a();

因为您声明var h two timesIs
if(false)
是为了做些什么?JS没有块级作用域,变量被提升。如果你不熟悉的话,可以考虑在吊装上阅读,这里的关键词是“吊装”。我想你可能没有抓住问题的关键。这段代码是专门设计用来显示某个行为的,OP想知道它为什么这样工作,而不是如何“修复”它。这与设置a的作用域h的行为不同问题的“解决方案”是在b的作用域中声明另一个具有h值的变量,并对其应用*2,但正如@JamesMontagne所说的,这不是问题的目的,对吧,我误解了。正如你们在四月份的同一时间发布的,但你们暗示a.h在b范围内不重要,在这种情况下,我接受了你们的建议
function a(){
    var h = 1;
    function b(){
        if(false){
            h = h * 2;
        }
        alert(h);
    }
    b();
}
a();