let 和 const
let 的特點
- let 的作用域在最近的 {} 之間
- 如果在 let a 之前使用 a 失驶,那么報錯(Temp Dead Zone)
- 如果重復(fù)let a , 會報錯
- let 存在塊級作用域
let 循環(huán)
for(let i = 0; i < 5;i++){
console.log(i) // 塊里面的i = 圓括號里面 i 的值
}
console.log(i) // Uncaught ReferenceError: i is not defined
const 特點
- const 的作用域在最近的 {} 之間
- 如果在 const a 之前使用 a ,那么報錯(Temp Dead Zone)
- 如果重復(fù)const a 荆几, 會報錯
- 只有一次賦值機(jī)會,并且必須在聲明的時候立馬賦值
- const聲明創(chuàng)建一個值的只讀引用唧取,在引用內(nèi)容是對象的情況下航夺,可以改變對象的內(nèi)容:
let user = { name: 'ZhangSan', age: 21 };
const USER_A = user;
console.log("USER_A :", USER_A ); // user: {name: "ZhangSan", age: 21}
user.age = 18;
console.log("USER_A :", USER_A ) // user: {name: "ZhangSan", age: 18}
解構(gòu)賦值
數(shù)組的解構(gòu)賦值
- 匹配 [ b, a ] = [ a, b ]
let [a,b,c] = [1,2,3] ;
console.log(a,b,c) // 1 2 3
let[a,[b],c] = [2,[3],4];
console.log(a,b,c) // 2,3,4
let [a,b,...rest] = [10,20,30,40,50]
console.log(rest) // [30, 40, 50]
- 交換變量
let a = 1;
let b = 2;
[a,b] = [b,a];
console.log(a,b) // 2 1
- 默認(rèn)值
let [a,b=2] = [3];
a // 3
b // 2 使用默認(rèn)值
let [a,b=2] = [3,4];
a // 3
b // 4 有對應(yīng)數(shù)值,使用對應(yīng)數(shù)值
undefined 和null 的區(qū)別:
var [a,b,c] = [1,2]
console.log(a,b,c) // 1 2 undefined
var [a,b,c] = [1,2, null]
console.log(a,b,c) // 1 2 null
let[a=2,b=3] = [undefined, null]
a // 2
b // null
- 函數(shù)傳參
let arr = [1,2];
function test([a,b]) {
console.log("a: " + a); // a: 1
console.log("b: " + b) // b: 2
}
test(arr)
對象的解構(gòu)賦值
- 對象匹配 let { a, b, c } = objABC
let { name , age} = {name: 'xxx',age: 18};
name // xxx
age // 18
- 對象匹配的同時重命名
let { name : username, age} = {name: 'xxx',age: 18};
username // xxx
age // 18
- 對象匹配 —— 改變原來的值
let name = 'ZhangSan';
let obj = {name: 'xxx',age: 18};
console.log(name); // ZhangSan
({ name, age } = obj ) ; // 這里要用()包住腥光,因為大括號會被解析成一個代碼塊報錯
console.log(name) // xxx
- 指定默認(rèn)值并重命名
let {a: A=1, b=2 } = {a: 99}
console.log(A) // 99
console.log(b) // 2
- 對象淺拷貝
let obj1 = { name: 'xxx',age: 18,others: {
fruits: 'xx1', book: 'wrrr' } };
let obj2 = {...obj1};
console.log(obj2) // {name: "xxx", age: 18,others: {fruits: 'xx1', book: 'wrrr' }}
- 對象合并 ...
let obj1 = {p1: 1, p2: 2};
let obj2 = {p2: 30, p3: 99};
let obj3 = Object.assign({},obj1,obj2);
console.log(obj3) // {p1: 1, p2: 30, p3: 99}
let obj4 = {...obj1,...obj2};
console.log(obj4) // {p1: 1, p2: 30, p3: 99}
參數(shù)處理
默認(rèn)參數(shù)值
函數(shù)默認(rèn)參數(shù)允許在沒有值或undefined被傳入時使用默認(rèn)形參关顷。
function sum(a=0,b=0){
console.log('a:'+a);
console.log('b:'+b);
return a + b
}
sum(1) // a:1 b:0 1
sum(2,6) // a:2 b:6 8
上面的代碼等價于:
function sum(a,b){
a = a || 0;
b = b || 0;
console.log('a:'+a);
console.log('b:'+b);
return a + b
}
剩余參數(shù)
展開運算符
先來看一個數(shù)組的擴(kuò)展:
var a = [1,2,3];
console.log(...a) ; // 1 2 3
var b = [...a,99,88];
console.log(b); // 對數(shù)組進(jìn)行擴(kuò)展 [1, 2, 3, 99, 88]
var c = b.concat(77,66);
console.log(c); // [1, 2, 3, 99, 88, 77, 66]
let arr1 = [1,2,3,4,5,6];
let [a,b,c,...arr2] = arr1;
console.log(arr2) // [4, 5, 6]
... 相當(dāng)于把數(shù)組拆開
- 函數(shù)參數(shù)的擴(kuò)展
function max(arr){
return Math.max(...arr)
}; // 求最大值
max([1,22,44,66,5,66,77,3,22,33,11,34]) // 77
function sort(...arr){
return arr.sort()
};
sort(1,2,5,3) // [1, 2, 3, 5]
- 類數(shù)組對象轉(zhuǎn)數(shù)組
ES5 寫法是:
let newArr = Array.prototype.slice.call(ArrayLike)
ES6 寫法如下:
let items = document.querySelectorAll('li');
Array.from(items).forEach((item) => console.log(item.innerText));
或者
let items = document.querySelectorAll('li');
[...items].forEach((item) => console.log(item.innerText))
模板字面量
多行字符串
let str = `
line1,
line2,
line3
`; // 注意這里的 ` 不是單引號
str // "
line1,
line2,
line3
"
字符串插值
let city = ' xxx';
let str = ` Hi
Welcome to ${city}.
` // 同樣的, 這里的 ` 不是單引號
str // " Hi
Welcome to xxx.
"
可以用來拼接HTML:
var data = [1,2,3,4];
var liArr = data.map((item) => `<li class="xxx"> 內(nèi)容 ${item}</li>`
).join('');
console.log(liArr); // <li class="xxx"> 內(nèi)容 1</li><li class="xxx"> 內(nèi)容 2</li><li class="xxx"> 內(nèi)容 3</li><li class="xxx"> 內(nèi)容 4</li>
var html = `<ul>${liArr}</ul>`;
console.log(html) // <ul><li class="xxx"> 內(nèi)容 1</li><li class="xxx"> 內(nèi)容 2</li><li class="xxx"> 內(nèi)容 3</li><li class="xxx"> 內(nèi)容 4</li></ul>
帶標(biāo)簽的模板字面量
如果一個模板字符串由表達(dá)式開頭武福,則該字符串被稱為帶標(biāo)簽的模板字符串议双,該表達(dá)式通常是一個函數(shù),它會在模板字符串處理后被調(diào)用捉片,在輸出最終結(jié)果前平痰,都可以通過該函數(shù)來對模板字符串進(jìn)行操作處理汞舱。
let name = 'xxx';
let score = 60;
let fn = function (){
console.log(arguments)
}
fn `${name} 的成績是 ${score}`
運行結(jié)果如下:
let name = 'xxx';
let score = 60;
let fn = function (){
let str = arguments[0];
let arg1 = arguments[1];
let arg2 = arguments[2];
if(arg2 >= 80){
return arg1 + str +arg2 + ',再接再厲哦宗雇!'
} else{
return arg1 + str + arg2 + '昂芜,要加油了哦!'
}
}
fn `${name} 的成績是 ${score}`
// "xxx, 的成績是 ,60赔蒲,要加油了哦泌神!"
把 name 和 score 改下:
name = 'x2';score = 90;
fn `${name} 的成績是 ${score}`
// "x2, 的成績是 ,90,再接再厲哦舞虱!"
原始字符串
在標(biāo)簽函數(shù)的第一個參數(shù)中欢际,存在一個特殊的屬性raw,我們可以通過它來訪問模板字符串的原始字符串矾兜,而不經(jīng)過特殊字符的替換损趋。
function tag(strings) {
console.log(strings.raw[0]);
}
tag`string text line 1 \n string text line 2`;
// string text line 1 \n string text line 2
原有字面量增強(qiáng)
- 更安全的二進(jìn)制字面量(0b1111101)
- 更安全的八進(jìn)制字面量(0o767)
- 字符串支持 Unicode
-- String.fromCodePoint
-- String.prototype.codePointAt - 正則表達(dá)式字面量添加 Unicode 支持(u 標(biāo)記)
- 正則表達(dá)式添加 y 標(biāo)記,支持粘滯匹配
對象屬性加強(qiáng)
屬性定義支持短語法 obj = { x, y }
ES5寫法:
var a = 1;
var b = 4;
var obj = {a:a,b:b} ;
obj // {a: 1, b: 4}
ES6寫法:
let a = 1;
let b = 4;
let obj = {a,b} ;
obj // {a: 1, b: 4}
屬性名支持表達(dá)式
動態(tài)屬性名
原來的寫法:
var name = 'a';
var obj = {};
obj[name] = 123;
obj // {a: 123}
ES6:
let name = 'a';
let obj = {[name]: 123};
obj // {a: 123}
屬性修飾符Object.defineProperty()
a === 1 && a ===2 && a === 3 問題
var i = 0;
Object.defineProperty(window,'a',{
get(){
i += 1;
return i
}
})
a === 1 && a ===2 && a === 3 // true
類 class
var Slider = {
append: function(){
console.log(1)
},
render: function(){
console.log(2)
}
}
ECMAScript 2015引入了一種對象方法的簡短寫法焕刮, "function" 關(guān)鍵字可以丟掉:
var Slider = {
append(){
console.log(1)
},
render(){
console.log(2)
}
}
構(gòu)造函數(shù)
class Cat {
constructor(name,personality){
this.name = name;
this.personality = personality;
} // 注意: 這里沒有逗號
sayHi (){ // 這個函數(shù)會放在原型上
console.log(`Hi,I'm a ${this.name}, I'm ${this.personality}`);
}
}
var BritishShorthair = new Cat('BritishShorthair','docile');
console.log(BritishShorthair); // {name: "BritishShorthair", personality: "docile"}
BritishShorthair.sayHi(); // Hi,I'm a BritishShorthair, I'm docile
上面的代碼等價于
function Cat(name,personality){
this.name = name;
this.personality = personality;
};
Cat.prototype.sayHi = function(){
console.log(`Hi,I'm a ${this.name}, I'm ${this.personality}`)
};
var BritishShorthair = new Cat('BritishShorthair','docile');
console.log(BritishShorthair); // Cat {name: "BritishShorthair", personality: "docile"}
BritishShorthair.sayHi(); // Hi,I'm a BritishShorthair, I'm docile
class 共有屬性不能是非函數(shù):
- 可以用原型寫
xxx.prototype.race = 'animal'
- get
class Cat {
constructor(name,personality){
this.name = name;
this.personality = personality;
}
get race (){
return 'animal'
}
}
let BritishShorthair = new Cat('BritishShorthair','docile');
BritishShorthair.race // animal
但是 不能通過 BritishShorthair.race = newvalue
來改
所以又要用到 set
class Cat {
constructor(name,personality){
this.name = name;
this.personality = personality;
this._race = `animal`;
}
get race (){
return this._race
}
set race(value){
this._race = value
}
}
let BritishShorthair = new Cat('BritishShorthair','docile');
再修改就發(fā)現(xiàn)改成功了:
如果想讓屬性只讀舶沿,就不寫set
ES6 模塊
用 import 和 export 寫好之后,
可以用webpack 或者 parcel (推薦) 打包 配并,然后引入
<script type="module" src="javascripts/app.js"></script> <!-- 已支持 ES6 模塊的瀏覽器 -->
<script nomodule src="dist/app.js"></script> <!-- 不支持 ES6 模塊的瀏覽器 -->
其他:
箭頭函數(shù)
JS 中的 Symbol 是什么括荡?
Generator函數(shù)的含義與用法
Thunk函數(shù)的含義與用法
co函數(shù)庫的含義與用法
async函數(shù)的含義與用法
tj/co