JavaScript平常会跳的坑系列
Posted
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了JavaScript平常会跳的坑系列相关的知识,希望对你有一定的参考价值。
function Foo() { //定义foo函数 getName = function () { console.log(‘1‘);}; console.log(this); return this; } Foo.getName = function () { console.log(‘2‘);}; //Foo创建了一个叫getName的静态属性存储了一个匿名函数 Foo.prototype.getName = function () { console.log(‘3‘);}; //Foo的原型对象新创建了一个叫getName的匿名函数 var getName = function () { console.log(‘4‘);}; //函数变量表达式创建了一个getName的函数 function getName() { console.log(‘5‘);} //声明一个叫getName函数 //由于变量定义提升,该段javascript实际上的解析顺序如下 /* function Foo() { //定义foo函数 getName = function () { console.log(‘1‘);}; console.log(this); return this; } var getName; function getName() { console.log(‘5‘);} Foo.getName = function () { console.log(‘2‘);}; //声明foo的getName静态属性 Foo.prototype.getName = function () { console.log(‘3‘);}; //以foo为原型再声明一个getName静态属性 getName = function () { console.log(‘4‘);}; */ Foo.getName(); //2 //析:访问Foo函数上存储的静态属性 getName(); //4 //由于变量定义提升,所有声明变量或声明函数都会被提升到当前函数的顶部,真正的执行顺序如下 /*var getName; function getName() { console.log(‘5‘);} getName = function () { console.log(‘4‘);}; */ Foo().getName(); //1 //析:考察变量作用域问题,this指向问题; //先执行了Foo函数,然后调用Foo函数的返回值对象的getName属性函数 //此时foo的返回值为Window对象 //Foo函数的第一句 getName = function () { alert (1); }; 是一句函数赋值语句,注意它没有var声明,所以先向当前Foo函数作用域内寻找getName变量,没有。再向当前函数作用域上层,即外层作用域内寻找是否含有getName变量,找到了,也就是第二问中的alert(4)函数,将此变量的值赋值为 function(){alert(1)}。 //此处实际上是将外层作用域内的getName函数修改了。 //注意:此处若依然没有找到会一直向上查找到window对象,若window对象中也没有getName属性,就在window对象中创建一个getName变量。 getName(); //1 //getName函数,相当于 window.getName() ,因为这个变量已经被Foo函数执行时修改了,遂结果与第三问相同,为1 new Foo.getName(); //2 //点(.)的优先级高于new操作,遂相当于是:new (Foo.getName)(); //所以实际上将getName函数作为了构造函数来执行,遂弹出2。 new Foo().getName(); //3 //析:Foo()返回的this是foo()对象,调用getName()匿名函数打印3 new new Foo().getName(); //3 //析: /*第七问, new new Foo().getName(); 同样是运算符优先级问题。 最终实际执行为: new ((new Foo()).getName)(); 先初始化Foo的实例化对象,然后将其原型上的getName函数作为构造函数再次new。 遂最终结果为3*/
以上是关于JavaScript平常会跳的坑系列的主要内容,如果未能解决你的问题,请参考以下文章
MacOS Sierra10.12.4编译Android7.1.1源代码必须跳的坑