Jve范围与Revealing Module Pattern有关

时间:2015-06-30 21:25:10

标签: javascript scope

还有一个JavaScript范围问题。我认为这与提升'无关。

我这里有一小段代码 - http://jsfiddle.net/0oqLzsec/2/

var c = function(){
    var x = 'before',
        callBefore = function(){
            alert(x);
        },
        callAfter = function(){
            _callAfter();
        };

    return{
        callBefore : callBefore,
        callAfter : callAfter
    }

    var y = 'after';

    function _callAfter(){
        alert(y);
    }
};

var obj = c();
obj.callBefore();
obj.callAfter();

callAfter()始终提醒“未定义”'即使变量y在_callAfter()之前定义。但是如果我在变量x之前移动变量y声明它正在工作。

我想知道下面定义的callAfter() _callAfter()是否可以Using MyConnection = New OleDbConnection("Provider=Microsoft.ACE.OLEDB.12.0;" + "Data Source=H:\Import\SER 2901 Fellow Cmts 063015B.xml;" + "Extended Properties=Excel 8.0;") Using MyCommand = New OleDbDataAdapter("select * from [SER export$]", MyConnection) Dim ds = New System.Data.DataSet MyCommand.Fill(ds) End Using End Using ,为什么它不能读取变量y?

2 个答案:

答案 0 :(得分:3)

_callAftery都被提升,这使得它们通过函数调用称为局部变量。 _callAfter函数可以被调用(就像你一样),它也会关闭变量y。但是,在从c函数返回之前,此变量未获得值已分配。因此,你得到undefined。如果您在返回前放置var y;,并在返回后放置y='after';,则相同。

换句话说,以下两个是等价的:



function foo(){
  var a;
  return function(){ return a };
  a = 42; // never runs
}
alert( foo()() );

function bar(){
  return function(){ return a };
  var a = 42;
}
alert( bar()() );




这是一个示例,显示局部变量被提升并关闭,即使函数文字出现在代码中的var之前:



function build() {
  return function(newValue) {
    alert("was: " + oldValue);
    oldValue = newValue;
    alert("now: " + oldValue);
  }
  var oldValue = 42;
}

f = build();
f(17);
// was: undefined
// now: 17

f(99);
// was: 17
// now: 99




答案 1 :(得分:2)

它与提升有关,var y被移动到函数的顶部,但是赋值(y = 'after')不是,所以它永远不会运行,因为它在{{{{1}之后1}}。

JS引擎将您的代码重写为:

return statement