1.下面的代碼將輸出什麼?
for (var i = 0; i < 5; i++) {
setTimeout(function() { console.log(i); }, i * 1000 );
}
閉包在這裏能起什麼做用?
上面的代碼不會按預期顯示值0,1,2,3,和4,
而是會顯示5,5,5,5,和5。
緣由是,在循環中執行的每一個函數將整個循環完成以後被執行,
所以,將會引用存儲在 i中的最後一個值,那就是5。
閉包能夠經過爲每次迭代建立一個惟一的範圍,
存儲範圍內變量的每一個惟一的值,
來防止這個問題,
以下:
for (var i = 0; i < 5; i++) {
(function(x) {
setTimeout(function() { console.log(x); }, x * 1000 );
})(i);
}
這就會按預期輸出0,1,2,3,和4到控制檯。
複製代碼
2.ES五、ES6和ES2015有什麼區別?
ES2015特指在2015年發佈的新一代JS語言標準,
ES6泛指下一代JS語言標準,
包含ES201五、ES201六、ES201七、ES2018等。
現階段在絕大部分場景下,
ES2015默認等同ES6。
ES5泛指上一代語言標準。
ES2015能夠理解爲ES5和ES6的時間分界線。
複製代碼
3.Iterator是什麼,有什麼做用?
Iterator是ES6中一個很重要概念,
它並非對象,
也不是任何一種數據類型。
由於ES6新增了Set、Map類型,
他們和Array、Object類型很像,Array、Object都是能夠遍歷的,
可是Set、Map都不能用for循環遍歷,
解決這個問題有兩種方案,
一種是爲Set、Map單獨新增一個用來遍歷的API,
另外一種是爲Set、Map、Array、Object新增一個統一的遍歷API,
顯然,
第二種更好,
ES6也就順其天然的須要一種設計標準,
來統一全部可遍歷類型的遍歷方式。
Iterator正是這樣一種標準。或者說是一種規範理念。
就好像JavaScript是ECMAScript標準的一種具體實現同樣,
Iterator標準的具體實現是Iterator遍歷器。
Iterator標準規定,全部部署了key值爲[Symbol.iterator],
且[Symbol.iterator]的value是標準的Iterator接口函數(標準的Iterator接口函數:
該函數必須返回一個對象,
且對象中包含next方法,
且執行next()能返回包含value/done屬性的Iterator對象)的對象,
都稱之爲可遍歷對象,
next()後返回的Iterator對象也就是Iterator遍歷器。
obj就是可遍歷的,
由於它遵循了Iterator標準,
且包含[Symbol.iterator]方法,
方法函數也符合標準的Iterator接口規範。
//obj.[Symbol.iterator]()
就是Iterator遍歷器
let obj =
{
data: [ 'hello', 'world' ], [Symbol.iterator]()
{ const self = this; let index = 0;
return { next() {
if (index < self.data.length) {
return { value: self.data[index++], done: false
};
} else {
return { value: undefined, done: true }; } } }; }
};
ES6給Set、Map、Array、String都加上了[Symbol.iterator]方法,
且[Symbol.iterator]方法函數也符合標準的Iterator接口規範,
因此Set、Map、Array、String默認都是能夠遍歷的。
//Array let array = ['red', 'green', 'blue']; array[Symbol.iterator]()
//Iterator遍歷器 array[Symbol.iterator]().next()
//{value: "red", done: false} //String let string = '1122334455'; string[Symbol.iterator]()
//Iterator遍歷器 string[Symbol.iterator]().next()
//{value: "1", done: false}
//set let set = new Set(['red', 'green', 'blue']); set[Symbol.iterator]()
//Iterator遍歷器
set[Symbol.iterator]().next()
{value: "red", done: false}
Map let map = new Map();
let obj= {map: 'map'};
map.set(obj, 'mapValue');
map[Symbol.iterator]().next()
{value: Array(2), done: false}
複製代碼
4.module、export、import是什麼,有什麼做用?
module、export、import
是ES6用來統一前端模塊化方案的設計思路和實現方案。
export、import的出現統一了前端模塊化的實現方案,
整合規範了瀏覽器/服務端的模塊化方法,
用來取代傳統的AMD/CMD、requireJS、seaJS、commondJS等等一系列前端模塊不一樣的實現方案,
使前端模塊化更加統一規範,
JS也能更加能實現大型的應用程序開發。
import引入的模塊是靜態加載(編譯階段加載)
而不是動態加載(運行時加載)。
import引入export導出的接口值是動態綁定關係,
即經過該接口,能夠取到模塊內部實時的值。
複製代碼
5.平常前端代碼開發中,有哪些值得用ES6去改進的編程優化或者規範?
一、經常使用箭頭函數來取代var self = this;的作法。
二、經常使用let取代var命令。
三、經常使用數組/對象的結構賦值來命名變量,結構更清晰,語義更明確,可讀性更好。
四、在長字符串多變量組合場合,用模板字符串來取代字符串累加,能取得更好地效果和閱讀體驗。
五、用Class類取代傳統的構造函數,來生成實例化對象。
六、在大型應用開發中,要保持module模塊化開發思惟,分清模塊之間的關係,經常使用import、export方法。
複製代碼