Sil*_*ian 5 javascript scope definition redefinition
考虑一下代码:
window.a = function(x){
var r = x*2;
window.a =alert; // redefines itself after first call
return r;
};
a('2 * 2 = '+a(2)); // doesn't work. it should've alerted "2 * 2 = 4"
Run Code Online (Sandbox Code Playgroud)
这也不起作用:
window.a = function(x){
alert(x);
window.a = function(x){ // redefines itself after first call
var r = x*2;
return r;
}
};
a('2 * 2 = '+a(2)); // doesn't work. it should've alerted "2 * 2 = 4"
Run Code Online (Sandbox Code Playgroud)
这两样都不是:
window.a = function(x){ alert(x); window.c = window.a; window.a = window.b; window.b = window.c; };
window.b = function(x){ var r = x*2; window.c = window.b; window.b = window.a; window.a = window.c; return r; };
a('2 * 2 = '+a(2)); // doesn't work.
Run Code Online (Sandbox Code Playgroud)
基本上我已经尝试了所有可行的方法,似乎都没有做到这一点.有人可以解释一下原因吗?
您正在成功地重新定义的功能,它只是表达调用它已经抓住了老函数的引用:这种情况发生在通话中表达的第一件事是,东西界定评估什么函数来调用,请参阅第11.2.3节的规格:
11.2.3函数调用
生产CallExpression:MemberExpression Arguments的计算方法如下:
- 让ref成为评估MemberExpression的结果.
- 让func为GetValue(ref).
- 设argList是评估Arguments的结果,产生一个参数值的内部列表(见11.2.4).
- 如果Type(func)不是Object,则抛出TypeError异常.
- 如果IsCallable(func)为false,则抛出TypeError异常.
- 如果Type(ref)是Reference,那么
a)如果IsPropertyReference(ref)为真,那么
i.让thisValue为GetBase(ref).
b)否则,ref的基础是环境记录
i.让thisValue成为调用GetBase(ref)的ImplicitThisValue具体方法的结果.- 否则,Type(ref)不是Reference.
a)让thisValue不确定.- 返回在func上调用[[Call]]内部方法的结果,提供thisValue作为此值并提供列表argList作为参数值.
在重新定义函数之前发生步骤1和2.
解决方案当然是按照您期望的顺序进行操作(实例 | 源代码):
window.a = function(x){
var r = x*2;
window.a =alert; // redefines itself after first call
return r;
};
var val = a(2);
a('2 * 2 = '+ val);
Run Code Online (Sandbox Code Playgroud)
旁注:有趣的是,您的第一个示例适用于Chrome(V8)(它也适用于IE6的JScript版本;但是,JScript有很多问题).它应该不起作用,并且不适用于Firefox(SpiderMonkey),Opera(Carakan)或IE9(Chakra).
归档时间: |
|
查看次数: |
486 次 |
最近记录: |