一起养成写作习惯!这是我参与「掘金日新计划 · 4 月更文挑战」的第17天,点击查看活动详情。
前端开发的第三年,突然发现,对于JS,我还有很多不懂的地方,趁着最近需求少,不如静下心来,从头把JS再学一遍,查漏补缺。
本系列以廖雪峰的《JavaScript教程》和《现代 JavaScript 教程》两个电子书作为线索,对其中需要进一步了解的知识,会阅读更多的文章,并作为扩展知识记录下来。
新手建议先阅读上面两个电子书,本系列更适合用来复习旧知识和查漏补缺。
通过下面的思维导图,我们先对JavaScript的数据类型和变量有一些基本的了解。
思维导图
通过下文的扩展阅读,我们进一步去了解更进一步的知识。
var变量提升
var的变量提升
console.log(a) // undefined
var a = 12
let的暂时性死区
(function() {
// let x 此时暂时性死区开始
console.log(x); // Uncaught ReferenceError: x is not defined
//暂时性死区结束
let x = 'child value'
}())
IIFE旧时var创建块级作用域的方法
原理是:创建了一个函数表达式并立即调用
// 创建 IIFE 的方法
(function() {
alert("Parentheses around the function");
})();
(function() {
alert("Parentheses around the whole thing");
}());
!function() {
alert("Bitwise NOT operator starts the expression");
}();
+function() {
alert("Unary plus starts the expression");
}();
参考文章
深入理解箭头函数
箭头函数没有this
箭头函数没有this,如果访问this,会取到外层的this。
let group = {
title: "Our Group",
students: ["John", "Pete", "Alice"],
showList() {
this.students.forEach(
student => alert(this.title + ': ' + student)
);
}
};
group.showList();
箭头函数没有arguments
在箭头函数内获取的arguments都是来自父作用域的。
例如下面的例子,defer(f, ms) 获得了一个函数,并返回一个包装器,该包装器将调用延迟 ms 毫秒,其中箭头函数的arguments是返回的函数的arguments。
function defer(f, ms) {
return function() {
setTimeout(() => f.apply(this, arguments), ms);
};
}
function sayHi(who) {
alert('Hello, ' + who);
}
let sayHiDeferred = defer(sayHi, 2000);
sayHiDeferred("John"); // 2 秒后显示:Hello, John
是否使用箭头函数,参考下面这个图,来自《You-Dont-Know-JS》
参考文章
JS的循环
常见的循环参考这篇讲的比较全的问题JS常用的循环遍历你会几种。
for-in为什么被ESLint告警
eslint有一条guard-for-in规则,这条规则要求for-in语句要包含一个if判断来判断object的key是否存在,以避免一些意外的错误。
此规则的错误代码示例:
/*eslint guard-for-in: "error"*/
for (key in foo) {
doSomething(key);
}
此规则的正确代码示例:
/*eslint guard-for-in: "error"*/
for (key in foo) {
if (Object.prototype.hasOwnProperty.call(foo, key)) {
doSomething(key);
}
}
for (key in foo) {
if ({}.hasOwnProperty.call(foo, key)) {
doSomething(key);
}
}
当然除了加判断,也可以直接改用Object.keys和forEach。
currentValues= {hey:1212, git:1212, nmo:12121}
Object.keys(currentValues).forEach(function(key) {
yield put(setCurrentValue(key, currentValues[key]));
})