为了账号安全,请及时绑定邮箱和手机立即绑定
首页 手记 你真的知道JS吗?

你真的知道JS吗?

2018.09.06 15:17 1363浏览

你真的知道JavaScript吗

    JavaScript是一门奇怪的语言,要真正掌握并不容易。废话不多说,来一个快速测试,5道题目,看看你对JavaScript是否真正掌握。准备好了吗?开始咯

题目

No.1

if (!("a" in window)) {    var a = 1;
}console.log(a);

No.2

var a = 1,
    b = function a(x) {
        x && a(--x);
    };console.log(a);

No.3

function a(x) {    return x * 2;
}var a;console.log(a);

No.4

function b(x, y, a) {    arguments[2] = 10;    console.log(a);
}
b(1, 2, 3);

No.5

function a() {    console.log(this);
}
a.call(null);

解析

No.1

    在浏览器环境中,全局变量都是window的一个属性,即
var a = 1 等价于 window.a = 1in操作符用来判断某个属性属于某个对象,可以是对象的直接属性,也可以是通过prototype继承的属性。
    再看题目,在浏览器中,如果没有全局变量 a ,则声明一个全局变量 a (ES5没有块级作用域),并且赋值为1。很多人会认为打印的是1。非也,大家不要忘了变量声明会被前置!什么意思呢?题目也就等价于

var a;if (!("a" in window)) {
    a = 1;
}console.log(a);

所以其实已经声明了变量a,只不过if语句之前值是undefined,所以if语句压根不会执行。
最后答案就是 undefined

No.2

这道题有几个需要注意的地方:

  1. 变量声明、函数声明会被前置,但是函数表达式并不会,准确说类似变量声明前置,举个栗子:

console.log('b', b); // b undefinedvar b = function() {}console.log('b', b); // b function () {}

2.具名的函数表达式的名字只能在该函数内部取到,举个例子(排除老的IE):

var foo = function bar () {}console.log('foo', foo); 
// foo function bar(){}console.log('bar', bar);// Uncaught ReferenceError: bar is not defined

    综合这两点,再看题目,最后输出的内容就为 1

No.3

函数声明会覆盖变量声明,但不会覆盖变量赋值,举个栗子简单粗暴:

function foo(){    return 1;
}var foo;console.log(typeof foo);    // "function"

函数声明的优先级高于变量声明的优先级,但如果该变量foo赋值了,那结果就完全不一样了:

function foo(){    return 1;
}var foo = 1;console.log(typeof foo);    // "number"

变量foo赋值以后,变量赋值初始化就覆盖了函数声明。这个需要注意
再看题目

function a(x) {    return x * 2;
}var a;console.log(a); // function a(x) {...}

No.4

这题考察 arguments 对象的用法(详看JavaScript中的arguments对象)
一般情况arguments与函数参数是动态绑定关系(为什么说是一般稍后会解释),所以很好理解,最后输出的是10

但是但是但是,我们不要忘了一个特殊情况--严格模式,在严格模式中 arguments 与相当于函数参数的一个拷贝,并没有动态绑定关系,举个栗子:

'use strict'// 严格模式!!function b(x, y, a) {    arguments[2] = 10;    console.log(a);
}
b(1, 2, 3); // 3

No.5

function a() {    console.log(this);
}
a.call(null);

关于 a.call(null); 根据ECMAScript262规范规定:
如果第一个参数传入的对象调用者是null或者undefined的话,call方法将把全局对象(浏览器上是window对象)作为this的值。所以,不管你什么时候传入null或者 undefined,其this都是全局对象window。所以,在浏览器上答案是输出 window 对象。

但是但是但是,我们依旧不能忘记一个特殊情况--严格模式,在严格模式中,null 就是 nullundefined 就是 undefined ,举个栗子:

'use strict';// 严格模式!!function a() {    console.log(this);
}
a.call(null); // nulla.call(undefined); // undefined

提醒

  1. 在浏览器中的全局对象是window,Node.js中是global;

  2. 为了使代码更加严谨与健壮,建议写JS都加上严格模式'use strict';

  3. ES6已经成为前端必备技能,呼吁大家都使用ES6,方便高效,可以使用babel把ES6转成ES5甚至ES3,尽量使用ES6推动前端的发展



作者:microzz
链接:https://www.jianshu.com/p/c4b3e29792b0


点击查看更多内容
0人点赞

若觉得本文不错,就分享一下吧!

评论

作者其他优质文章

正在加载中
手记
粉丝
86
获赞与收藏
455

关注TA,一起探索更多经验知识

同主题相似文章浏览排行榜

风间影月说签约讲师

51篇手记,涉及Java、MySQL、Redis、Spring等方向

进入讨论

Tony Bai 说签约讲师

151篇手记,涉及Go、C、Java、Python等方向

进入讨论
感谢您的支持,我会继续努力的~
扫码打赏,你说多少就多少
赞赏金额会直接到老师账户
支付方式
打开微信扫一扫,即可进行扫码打赏哦
意见反馈 帮助中心 APP下载
官方微信

举报

0/150
提交
取消