摘要:以前現(xiàn)在創(chuàng)建一個叫做的變量,值是數(shù)組中第一個對象中鍵的值。以前用的時候使用鏈式來處理這種連續(xù)請求。一個可以一個,并且等待結(jié)果以后再進行下一步。并且一請求到就立即打印結(jié)果,并不等待后續(xù)的請求完成。
String Template Strings
連接String更方便直觀。使用反引號包括要生成的String,使用${}包括具體變量。
var name = "Yixuan"; var email = "yixuan124@gmail.com"; var title = "Student"; //以前 var msg = "Welcome! Your " + title + " is " + name + ", contact: " + email + "."; //現(xiàn)在 var msg = `Welcome! Your ${title} is ${name}, contact: ${email}.` //Welcome! Your name is Yixuan, contact: yixuan124@gmail.com.Tagged Templates
在模版字符串前調(diào)用自定函數(shù),來定制模版字符串的解析方式。這個函數(shù)的第一個函數(shù)包含一個字符串值的數(shù)組,其余的參數(shù)是一系列的$表達式的引用變量,可以用...操作來把這些參數(shù)當成一個數(shù)組。
這個例子中我們的自定函數(shù)formatCurrency將字符串中的數(shù)字加上了$符號并保留兩位小數(shù)。
var amount = 4.2; var msg = formatCurrency`The total for your order is ${amount}.` function formatCurrency(strings, ...values) { var str = ""; //console.log(strings); for (let i = 0; i < strings.length; i++) { str += strings[i]; if( i < values.length){ console.log(typeof values[i]); if(typeof values[i] == "number") { str += `$${values[i].toFixed(2)}`; }else { str += values[i]; } } } return str; } console.log(msg); //The total for your order is $12.30.String Padding & String Trimming
JS標準庫中現(xiàn)在自帶給字符串兩邊加內(nèi)容和刪減空格的方法。
padStart給字符串左邊加內(nèi)容,padEnd給字符串右邊加內(nèi)容。
var str = "Hello"; str.padStart(5); // "Hello" str.padStart(8) // " Hello" str.padStart(8, "*"); // "***Hello" str.padStart(8, "12345"); // "123Hello" str.padStart(8, "ab"); // abaHello" str.padEnd(8) // "Hello " str.padEnd(8, "*") // "Hello***" str.padEnd(8, "ab"); // "Helloaba"
trimStart去除左邊空格, trimEnd去除右邊空格。
var str = " some stuff "; str.trim(); // "some stuff" str.trimStart(); // "some stuff " str.trimEnd(); // " some stuff"Destructuring
有時我們get到了一個很大的JSON對象,我們需要把里面的一些值分配到變量當中。解構(gòu)讓這個操作更方便。
看一個例子。
var tmp = getSomeRecords(); //tmp是一個擁有兩個對象的數(shù)組。 //以前 var first = tmp[0]; var second = tmp[1]; var firstName = first.name; var firstEmail = first.email !== undefined ? first.email : "no email"; var secondName = second.name; var secondEmail = second.email !== undefined ? first.email : "no email"; //現(xiàn)在 var [ {// 創(chuàng)建一個叫做firstName的變量,值是數(shù)組中第一個對象中name鍵的值。 name: firstName, // 創(chuàng)建一個叫做firstEmail的變量,值是數(shù)組中第一個對象中email鍵的值,如果沒有這個鍵則使用默認值“no email"。 email: firstEmail = "no email" }, { name: secondName, email: secondEmail = "no email" } ] = tmp;
注意在這個例子中,賦值等號左邊的[],這個中括號不代表數(shù)組,而代表一種解構(gòu)賦值的pattern模式。還有要注意的是像上面這個例子的email的默認值只會在檢測到undefined的時候才會被使用,如果值是null,不會觸發(fā)使用默認值。
看一個更簡單的例子。
function data(){ return [1,2,3]; } // 以前 var tmp = data(); var first = tmp[0]; var second = tmp[1]; var third = tmp[2]; //現(xiàn)在 var [ first, second, third ] = data();
如果左邊的變量比右邊的值多,多余的變量的值就會是undefined。如果左邊的變量比右邊的值少,多余的值會被忽略。
如果我們要在一個變量里多賦幾個值呢?
data = [1,2,3,4,5]; var [ first, second, third, ...fourth ] = data; //這里fourth是[4,5];
如果值不夠
data =[1,2,3]; var [ first, second, third, ...fourth ] = data; //這里fourth是空數(shù)組[];
有的時候我們需要交換變量的值,用解構(gòu)也更方便。
var x = 10; var y = 20; //以前 var tmp = x; x = y; y = tmp; //現(xiàn)在 ] [y,x] = [x,y];
有的時候我們將一個數(shù)組傳入函數(shù)的時候,我們只需要它的前三個元素,我們也可以使用解構(gòu),在函數(shù)參數(shù)聲明的時候就做到這步。
function data([ first, second, third ]) { }
解構(gòu)賦值如果出現(xiàn)賦值錯誤,和普通賦值一樣,也會報錯。
var data = null; var [first, second] = data; //TypeError function foo([first,second]) } { ... } foo(data);//傳入null //TypeError
這個時候我們需要Graceful Fallback(降級,向下兼容)
var data = null; var [first, second] = data || []; //不報錯 function foo([first,second] = []) } { ... } //不報錯
嵌套解構(gòu)
var data = [1,[2,3],4]; var [ first, [ second, third ], fourth ] = data;Object Destructuring
有的時候我們有一個默認的對象,但是我們需要根據(jù)一個新傳過來的對象,來創(chuàng)建一個新對象。舉個例子,我們知道的表單信心有name,wechat,phone,gender等屬性(鍵名),但是有時表單會有新的屬性。這是我們可以用解構(gòu)賦值來很好的創(chuàng)建出一個新對象,來傳到后端或傳到數(shù)據(jù)庫。
function makeObject({ name = "default name", wechat = "default wechat", phone = "default phone", gender = "none", ...otherProps } = {}) { return { name, wechat, phone, gender, ...otherProps } } const obj = { name: "wyx", wechat: "weixin", gender: "male", age:"22", year:"2019" } const newObj = makeObject(obj); console.log(newObj); /* { name: "wyx", wechat: "weixin", phone: "default phone",//沒有的屬性使用默認值 gender: "male", age: "22", year: "2019" } */Array Array.find()
找到數(shù)組中相應(yīng)的值,如果有就返回這個值,沒有就undefined。
var arr = [{a:1},{a:2}]; var res = arr.find(v => v && v.a > 1); console.log(res); // {a:2} res = arr.find(v => v && v.a > 10); console.log(res); // undefinedArray.findIndex()
找到相應(yīng)值的index
var arr = ["a","b","c","d"]; var res = arr.findIndex(v => v && v == "c"); console.log(res); // 2 res = arr.findIndex(v => v && v == "x"); console.log(res); // -1Array.includes()
用來代替以前的Array.indexOf(xxx) != -1
var arr = [10,20,30,40]; //以前 if(arr.indexOf(30) != -1){ console.log("exist!"); } //現(xiàn)在 if(arr.includes(30)) { console.log("exist!"); } //exist!Array.flat()
攤開數(shù)組,可以根據(jù)傳入?yún)?shù)改變具體攤開的層數(shù)。默認攤開一層。
var nestedArray = [1,2,[3,4],[5,[6,7]]]; nestedValues.flat(0); //[1,2,[3,4],[5,[6,7]]] nestedValues.flat(); //default 1 //[1,2,3,4,5,[6,7]] nestedValues.flat(2); //[1,2,3,4,5,6,7];Array.flatMap()
flatMap只能攤開一層,如果需要更多層,需要分開使用map()和flat().
[1,2,3,4,5,6].flatMap(v => { if (v % 2 == 0) { return [v, v * 2]; } else { return []; } }) //[2,4,4,8,6,12]Iterator Built-in Iterable
Iterator簡單來說,就是我們用next()來遍歷一個集合。
在ES6中,String, Array, TypedArray,Map, Set是默認iterable的。
var str = "Hi" //在string上使用iterator var it1 = str[Symbol.iterator](); //這里Symbol.iterator是str對象的一個屬性,我們通過[Symbol.iterator]獲取到這個對象的iterator然后把它賦給it1。 it1.next(); // { value: "H", done: false} it2.next(); // { value: "i", done: false} it3.next(); // { valye: undefinedn done:true} var arr = ["H","i"]; //在Array上使用iterator var it2 = arr[Symbol.iterator](); it2.next(); // {value : "H", done: false} it2.next(); // {value : "i", done: false} it2.next(); // {value : undefined, done: true}Declarative Iterators
for of 循環(huán)其實就是使用了iterator
var str = "Hello"; var it = str[Symbol.iterator](); //在for loop中使用iterator for(let v of it){ console.log(v); } //效果和直接使用for loop是一樣的 for (let v of str) { console.log(v); }
...符號也使用iterator
var str ="Hello"; var letters = [...str]; console.log(letters); // ["H","e","l","l","o"]Object類型沒有iterator
我們在js中最常使用的對象類型,沒有默認的iterator,我們需要自己定義一個。
var obj = { a : 1, b : 2, c : 3 } for (let v of obj) { console.log(v); } // TypeError! //想要使用for of循環(huán)的時候出現(xiàn)了錯誤 //定義iterator屬性 obj[Symbol.iterator] = function(){ let keys = Object.keys(this); let index = 0; return { next: () => { if(index < keys.length){ return { done : false, value : keys[index++] } }else { return { done : true, value : undefined } } } }; } console.log([...obj]); //["a","b","c"]Generators Generators
function *generate() { yield 1; yield 2; yield 3; return 4; } var it = generate(); it.next(); // {value: 1, done : false} it.next(); // {value: 2, done : false} it.next(); // {value: 3, done : false} it.next(); // {value: 4, done : true} console.log([...generate()]); // [1,2,3]
一個使用生成器的例子,這里我們給luckyNumbers對象一個我們自定義的生成器函數(shù)叫l(wèi)ucky,然后在調(diào)用這個生成器的時候使用...操作符來iterate這個生成器,打印1-30之間6的倍數(shù)。
var luckyNumbers = { *lucky({ start = 0, end = 100, step = 1 } = {}) { for (let i = start; i <= end; i+= step) { yield i; } } }; console.log(`My lucky numbers are: ${ [...luckyNumbers.lucky({ start: 6, end: 30, step: 4 })] }`) //My lucky numbers are: 6,10,14,18,22,26,30Async Await Async出現(xiàn)的歷史
這里有一個例子,我們先請求當前當前用戶,獲得用戶數(shù)據(jù)以后,又請求當前用戶所下過訂單和進行中的訂單的例子。
以前用Promise的時候,使用鏈式then()來處理這種連續(xù)請求。
fetchCurrentUser() .then(function onUser(user) { //獲得當前用戶 return Promise.all([ //用Promise.all來做兩個請求,返回的還是一個promise,如果有一個請求中有一個reject則都reject fetchArchivedOrders( user.id ), fetchCurrentOrders (user.id) ]); })
后來我們有人不再用鏈式then()來處理多個請求。而是用generator來獲得多個請求的response。一個generator可以yield一個promise,并且等待yield結(jié)果以后再進行下一步。但是這個方法一般要使用第三方庫的一種runner函數(shù)進行,像Co,Koa都有。runner函數(shù)的作用就是在yield的時候等待結(jié)果resolve,然后再往下iterate,往下yield。
runner(function *main() { var user = yield fetchCurrentUser(); var [ archivedOrders, currentOrders ] = yield Promise.all([ fetchArchivedOrders( user.id ), fetchArchivedOrders( user.id ) ]) });
其實上面這個例子里的yield關(guān)鍵詞,已經(jīng)很像await關(guān)鍵詞了,所以后來JS官方就推出了Async Await關(guān)鍵詞,不再需要用第三方庫的runner函數(shù)。
async function main() { var user = await fectchCurrentUser(); var [archiveOrders, currentOrders] = await Promise.all([ fetchArchiveOrders(user.id), fetchCurrentOrders(user.id) ]); return archiveOrders + currentOrders; }
這里有個例子,我們同時請求三個file,但是保證打印結(jié)果是按順序打印,也沒有undefined。并且一請求到就立即打印結(jié)果,并不等待后續(xù)的請求完成。
function getFile(file) { return new Promise(function(resolve){ fakeAjax(file,resolve); }); } async function loadFiles(files) { var prs = files.map(getFile); //用map同時做三個請求 for (let pr of prs) { console.log(await pr); } //在for loop中加入await關(guān)鍵詞,來確保按順序打印,也不會undefined。 } loadFiles(["files","file2","file3"]);async await problems
async await也有一些問題
await只能應(yīng)對Promise
Starvation
promise會在時間循環(huán)中排進microtask,會造成饑餓陷阱,這里不多寫。
cancelation
Async函數(shù)是沒有辦法被手動取消的,比如一個request要下載巨大的文件,async函數(shù)過程就會一直進行
文章版權(quán)歸作者所有,未經(jīng)允許請勿轉(zhuǎn)載,若此文章存在違規(guī)行為,您可以聯(lián)系管理員刪除。
轉(zhuǎn)載請注明本文地址:http://m.hztianpu.com/yun/104670.html
摘要:學(xué)習定稿有兩年多的時間了,斷斷續(xù)續(xù)通過一些博客,書籍也學(xué)到了很多知識。將各個部分的知識整理成一篇篇博文,以便于自己系統(tǒng)掌握和復(fù)習。整個系列主要參考了的深入理解,可以看作是對這本書的一個學(xué)習總結(jié),也向大家強烈推薦這本書作為的學(xué)習書籍。 學(xué)習es6 es6定稿有兩年多的時間了,斷斷續(xù)續(xù)通過一些博客,書籍也學(xué)到了很多es6知識??梢哉f,es6給js語言帶來了非常大的改進,引進了很多好用的特性...
摘要:聲明之函數(shù)作用域和全局作用域。塊級作用域不能重復(fù)聲明臨時性死區(qū)等特性用來解決變量存在的種種問題。塊級作用域終于在外面訪問不到了。一些常量聲明使用聲明的變量名全部大寫。 ES5之前javascript語言只有函數(shù)作用域和全局作用域,使用var來聲明變量,var聲明的變量還存在變量提升使人困惑不已。我們先來復(fù)習一下ES5的var聲明,再對比學(xué)習let和const 。 var var聲明之函...
摘要:結(jié)合工作中使用情況,簡單對進行一些復(fù)習總結(jié),包括常用的語法,等,以及短時間內(nèi)要上手需要重點學(xué)習的知識點不同工作環(huán)境可能有一些差別,主要參考鏈接是阮一峰的博客以及外文博客阮老師大部分文章是直接翻譯的這個博客簡介先說一下,是一個標準化組織,他們 結(jié)合工作中使用情況,簡單對es6進行一些復(fù)習總結(jié),包括常用的語法,api等,以及短時間內(nèi)要上手需要重點學(xué)習的知識點(不同工作環(huán)境可能有一些差別),...
摘要:的暑期實習面試到現(xiàn)在差不多都結(jié)束了,算下來自己也投了十幾家簡歷,經(jīng)歷的差不多十場筆試,現(xiàn)場和電話面試也差不多有五六家公司。阿里三面三面不知道是不是交叉面,不過這次面試面試官說他是北京的之前都是杭州。 2017的暑期實習面試到現(xiàn)在差不多都結(jié)束了,算下來自己也投了十幾家簡歷,經(jīng)歷的差不多十場筆試,現(xiàn)場和電話面試也差不多有五六家公司。雖然最后只拿到兩個offer,所幸是自己期待的公司,下面從...
閱讀 1543·2019-08-30 15:44
閱讀 2003·2019-08-30 14:07
閱讀 2955·2019-08-30 13:56
閱讀 2428·2019-08-29 17:06
閱讀 1404·2019-08-29 14:13
閱讀 2139·2019-08-29 11:28
閱讀 3303·2019-08-26 13:56
閱讀 2016·2019-08-26 12:11