资讯专栏INFORMATION COLUMN

一道前端JS题目

2json / 3127人阅读

摘要:返回值对象指代的是调用这个函数的对象,在这里相当于,则相当于而的已经被赋值为,所以结果就为。

做过很多前端笔试题,有些题看起来简单,就是读程序写结果,但要么做错,要么对答案不确定,这里找到一道比较综合的题目

function Foo() {  //定义了一个名叫Foo的函数
    getName = function () { alert (1); };   //(1)函数内定义了一个函数变量
    return this;
}     
Foo.getName = function () { alert (2);};  //(2)创建了Foo的静态属性
Foo.prototype.getName = function () { alert (3);};  //(3)定义了Foo函数原型对象上的getName函数
var getName = function () { alert (4);};  //(4)通过函数变量表达式定义了一个叫getName的函数
function getName() { alert (5);}   //(5)声明了一个getName函数

//请写出以下输出结果:
Foo.getName();
getName();
Foo().getName();
getName();
new Foo.getName();
new Foo().getName();
new new Foo().getName();

第一题:

Foo.getName(); //2
Foo.getName; // function(){alert(2);}

这道题比较简单,Foo函数上的getName函数,执行的是第(2)句

第二题:

getName(); //4

我多次做这道题都会认为答案是5,其实不然。
因为变量声明提升,所以(4)拆分成两句,var getName; getName = function(){alert(3);}
其中var getName函数表达式被提升,但getName = function(){alert(3);}则不提升,(5)函数声明function getName同样提升,结果顺序就变为

function Foo() {  
    getName = function () { alert (1); };   
    return this;
}
var getName;  //变量声明提升
function getName () {alert(5);};     //变量声明提升,getName()的结果为alert(5)
Foo.getName = function () { alert (2);}; 
Foo.prototype.getName = function () { alert (3);};  
getName = function () { alert (4);};   //覆盖了getName()的结果

因此,getName()的结果为4.

第三题

Foo().getName(); //1

先执行Foo()函数,再调用其返回值对象的getName属性函数。
(1)句没有var声明,就先在Foo()里寻找getName声明,没有找到,就在外层作用域中寻找,在第(4)句找到了var getName,将此变量的值赋值为function(){alert(1);}
Foo()返回值对象this指代的是调用这个函数的对象,在这里相当于window,则Foo().getName()相当于window.getName(),而windowgetName()已经被赋值为function(){alert(1);},所以结果就为1。

Foo.getNameFoo().getName的区别

function Foo(){
    var getName = "Zoe";
}
Foo.getName; //undefined
Foo().getName; //"Zoe"

第四题

getName(); //相当于调用window.getName(),结果为1

第五题

new Foo.getName(); //2

成员访问运算符(.)的优先级大于new,小括号()的优先级又大于(.)
所以问题改写成

new (Foo.getName)();相当于把getName当做构造函数在执行

第六题

new Foo().getName(); //3

同样因为优先级,改写成

(new Foo()).getName();

var f = Foo();
f.getName();

首先构建了一个Foo函数的实例化对象,再调用对象的getName属性,由于Foo构造函数没有添加getName属性,所以向上查找到原型对象,即(3)句,得到结果3
我犯过的一个错误,将(1)看成Foo函数的属性,其实不是的,那只是函数体内的一个变量,只能在函数体内访问,如果要表示函数属性,需要写成this.getName

第七题

new new Foo().getName(); //3

改写成

new ((new Foo()).getName)();

var f = new Foo();  
var x = f.getName;
new x(); 

文章版权归作者所有,未经允许请勿转载,若此文章存在违规行为,您可以联系管理员删除。

转载请注明本文地址:https://www.ucloud.cn/yun/80483.html

相关文章

  • 由浅入深的前端面试题 和矫情的“浪漫主义”诗句

    摘要:好吧,我承认太标题党了,这篇文章是通过一道前端面试题引出的纯技术讨论。我先要矫情无比的从中外诗歌说起。这一星期陆陆续续面试了不少于个人,其中不乏工作履历突出的候选者。这样做的问题在于循环并没有要求枚举对象的修改与当前循环保持一致。 好吧,我承认太标题党了,这篇文章是通过一道前端面试题引出的纯技术讨论。我先要矫情无比的从中外诗歌说起。 传统的佛学经典里,被世人熟知的有这样一句话:一花一世...

    JerryZou 评论0 收藏0
  • 由浅入深的前端面试题 和矫情的“浪漫主义”诗句

    摘要:好吧,我承认太标题党了,这篇文章是通过一道前端面试题引出的纯技术讨论。我先要矫情无比的从中外诗歌说起。这一星期陆陆续续面试了不少于个人,其中不乏工作履历突出的候选者。这样做的问题在于循环并没有要求枚举对象的修改与当前循环保持一致。 好吧,我承认太标题党了,这篇文章是通过一道前端面试题引出的纯技术讨论。我先要矫情无比的从中外诗歌说起。 传统的佛学经典里,被世人熟知的有这样一句话:一花一世...

    lk20150415 评论0 收藏0
  • 面试完前端工程师被打击,回来补一下

    摘要:去公司面试前端,给了一套题,一看,大体上不会,跟面试官说这题对我有些难,他说这是基础,你可以走了,于是我走了。回来查了才知道原来数组就有方法。一查我再掩面而泣,原来里就带了就可以干这活。 去XX公司面试前端,给了一套题,一看,大体上不会,跟面试官说这题对我有些难,他说这是基础,你可以走了,于是我走了。人艰不拆啊。 但是作为一个知错就改的好少年,我要发扬不懂就问,不懂就去研究的优良传统...

    hosition 评论0 收藏0
  • 一道前端面试题引发的思考

    摘要:直接开始题目是厉害了说句实话开发中谁写成这样保证会被打死。不过面试就是面试,有面试官的考量点。官方是这么说的。结果完美,不过小姐姐的意思是数组的方法会自动触发数组的。 直接开始题目是 if(a==1 && a==2 && a==3){ alert(厉害了) } 说句实话开发中谁写成这样保证会被打死。 不过面试就是面试,有面试官的考量点。 我理解的点有两个 1、隐式类型转换 先说...

    gaomysion 评论0 收藏0

发表评论

0条评论

2json

|高级讲师

TA的文章

阅读更多
最新活动
阅读需要支付1元查看
<