ES6新增的內容之前的都是 ES5 的內容接下來我們聊一下 ES6 的內容let 和 const 關鍵字我們以前都是使用 var 關鍵字來宣告變數的在 ES6 的時候,多了兩個關鍵字 let 和 const,也是用來宣告變數的只不過和 var 有一些區別
1、let 和 const 不允許重複宣告變數
// 使用 var 的時候重複宣告變數是沒問題的,只不過就是後面會把前面覆蓋掉 var num = 100 var num = 200
// 使用 let 重複宣告變數的時候就會報錯了let num = 100let num = 200 // 這裡就會報錯了// 使用 const 重複宣告變數的時候就會報錯const num = 100const num = 200 // 這裡就會報錯了
2、let 和 const 宣告的變數不會在預解析的時候解析(也就是沒有變數提升)
// 因為預解析(變數提升)的原因,在前面是有這個變數的,只不過沒有賦值console.log(num) // undefinedvar num = 100
// 因為 let 不會進行預解析(變數提升),所以直接報錯了console.log(num) // undefinedlet num = 100
// 因為 const 不會進行預解析(變數提升),所以直接報錯了console.log(num) // undefinedconst num = 100
3、let 和 const 宣告的變數會被所有程式碼塊限制作用範圍
// var 宣告的變數只有函式能限制其作用域,其他的不能限制if (true) { var num = 100}console.log(num) // 100
// let 宣告的變數,除了函式可以限制,所有的程式碼塊都可以限制其作用域(if/while/for/...)if (true) { let num = 100 console.log(num) // 100}console.log(num) // 報錯
// const 宣告的變數,除了函式可以限制,所有的程式碼塊都可以限制其作用域(if/while/for/...)if (true) { const num = 100 console.log(num) // 100}console.log(num) // 報錯
let 和 const 的區別1、let 宣告的變數的值可以改變,const 宣告的變數的值不可以改變
let num = 100num = 200console.log(num) // 200
const num = 100num = 200 // 這裡就會報錯了,因為 const 宣告的變數值不可以改變(我們也叫做常量)
2、let 宣告的時候可以不賦值,const 宣告的時候必須賦值
let numnum = 100console.log(num) // 100
const num // 這裡就會報錯了,因為 const 宣告的時候必須賦值
箭頭函式箭頭函式是 ES6 裡面一個簡寫函式的語法方式重點: 箭頭函式只能簡寫函式表示式,不能簡寫宣告式函式
function fn() {} // 不能簡寫const fun = function () {} // 可以簡寫const obj = { fn: function () {} // 可以簡寫}
語法: (函式的行參) => { 函式體內要執行的程式碼 }
const fn = function (a, b) { console.log(a) console.log(b)}// 可以使用箭頭函式寫成const fun = (a, b) => { console.log(a) console.log(b)}const obj = { fn: function (a, b) { console.log(a) console.log(b) }}// 可以使用箭頭函式寫成const obj2 = { fn: (a, b) => { console.log(a) console.log(b) }}
箭頭函式的特殊性箭頭函式內部沒有 this,箭頭函式的 this 是上下文的 this// 在箭頭函式定義的位置往上數,這一行是可以打印出 this 的// 因為這裡的 this 是 window// 所以箭頭函式內部的 this 就是 windowconst obj = { fn: function () { console.log(this) }, // 這個位置是箭頭函式的上一行,但是不能打印出 this fun: () => { // 箭頭函式內部的 this 是書寫箭頭函式的上一行一個可以打印出 this 的位置 console.log(this) }}obj.fn()obj.fun()
按照我們之前的 this 指向來判斷,兩個都應該指向 obj但是 fun 因為是箭頭函式,所以 this 不指向 obj,而是指向 fun 的外層,就是 window箭頭函式內部沒有 arguments 這個引數集合
const obj = { fn: function () { console.log(arguments) }, fun: () => { console.log(arguments) }}obj.fn(1, 2, 3) // 會列印一個偽陣列 [1, 2, 3]obj.fun(1, 2, 3) // 會直接報錯
函式的行參只有一個的時候可以不寫 () 其餘情況必須寫
const obj = { fn: () => { console.log('沒有引數,必須寫小括號') }, fn2: a => { console.log('一個行參,可以不寫小括號') }, fn3: (a, b) => { console.log('兩個或兩個以上引數,必須寫小括號') }}
函式體只有一行程式碼的時候,可以不寫 {} ,並且會自動 returnconst obj = { fn: a => { return a + 10 }, fun: a => a + 10}console.log(fn(10)) // 20console.log(fun(10)) // 20
函式傳遞引數的時候的預設值我們在定義函式的時候,有的時候需要一個預設值出現就是當我不傳遞引數的時候,使用預設值,傳遞引數了就使用傳遞的引數
function fn(a) { a = a || 10 console.log(a)}fn() // 不傳遞引數的時候,函式內部的 a 就是 10fn(20) // 傳遞了引數 20 的時候,函式內部的 a 就是 20
在 ES6 中我們可以直接把預設值寫在函式的行參位置
function fn(a = 10) { console.log(a)}fn() // 不傳遞引數的時候,函式內部的 a 就是 10fn(20) // 傳遞了引數 20 的時候,函式內部的 a 就是 20
這個預設值的方式箭頭函式也可以使用
const fn = (a = 10) => { console.log(a)}fn() // 不傳遞引數的時候,函式內部的 a 就是 10fn(20) // 傳遞了引數 20 的時候,函式內部的 a 就是 20
注意: 箭頭函式如果你需要使用預設值的話,那麼一個引數的時候也需要寫 ()解構賦值解構賦值,就是快速的從物件或者陣列中取出成員的一個語法方式解構物件快速的從物件中獲取成員// ES5 的方法向得到物件中的成員const obj = { name: 'Jack', age: 18, gender: '男'}let name = obj.namelet age = obj.agelet gender = obj.gender
// 解構賦值的方式從物件中獲取成員const obj = { name: 'Jack', age: 18, gender: '男'}// 前面的 {} 表示我要從 obj 這個物件中獲取成員了// name age gender 都得是 obj 中有的成員// obj 必須是一個物件let { name, age, gender } = obj
解構陣列快速的從陣列中獲取成員
// ES5 的方式從陣列中獲取成員const arr = ['Jack', 'Rose', 'Tom']let a = arr[0]let b = arr[1]let c = arr[2]
// 使用解構賦值的方式從陣列中獲取成員const arr = ['Jack', 'Rose', 'Tom']// 前面的 [] 表示要從 arr 這個陣列中獲取成員了// a b c 分別對應這陣列中的索引 0 1 2// arr 必須是一個數組let [a, b, c] = arr
注意{} 是專門解構物件使用的[] 是專門解構陣列使用的不能混用模版字串ES5 中我們表示字串的時候使用 '' 或者 ""在 ES6 中,我們還有一個東西可以表示字串,就是 ``(反引號)let str = `hello world`console.log(typeof str) // string
和單引號好友雙引號的區別
1、反引號可以換行書寫
// 這個單引號或者雙引號不能換行,換行就會報錯了let str = 'hello world' // 下面這個就報錯了let str2 = 'hello world'
let str = ` hello world`console.log(str) // 是可以使用的
2、反引號可以直接在字串裡面拼接變數
// ES5 需要字串拼接變數的時候let num = 100let str = 'hello' + num + 'world' + numconsole.log(str) // hello100world100// 直接寫在字串裡面不好使let str2 = 'hellonumworldnum'console.log(str2) // hellonumworldnum
// 模版字串拼接變數let num = 100let str = `hello${num}world${num}`console.log(str) // hello100world100
在 `` 裡面的 ${} 就是用來書寫變數的位置
展開運算子ES6 裡面號新添加了一個運算子 ... ,叫做展開運算子作用是把陣列展開let arr = [1, 2, 3, 4, 5]console.log(...arr) // 1 2 3 4 5
合併陣列的時候可以使用
let arr = [1, 2, 3, 4]let arr2 = [...arr, 5]console.log(arr2)
也可以合併物件使用
let obj = { name: 'Jack', age: 18}let obj2 = { ...obj, gender: '男'}console.log(obj2)
在函式傳遞引數的時候也可以使用
let arr = [1, 2, 3]function fn(a, b, c) { console.log(a) console.log(b) console.log(c)}fn(...arr)// 等價於 fn(1, 2, 3)
Map 和 Set是 ES6 新增的兩個資料型別都是屬於內建建構函式使用 new 的方式來例項化使用Set使用方式就是和 new 連用
const s = new Set()console.log(s)/* Set(0) {} size: (...) __proto__: Set [[Entries]]: Array(0) length: 0*/
就是一個數據集合我們可以在 new 的時候直接向內部新增資料// 例項化的時候直接新增資料要以陣列的形式新增const s = new Set([1, 2, 3, {}, function () {}, true, 'hwllo'])console.log(s)/* Set(7) {1, 2, 3, {…}, ƒ, …} size: (...) __proto__: Set [[Entries]]: Array(7) 0: 1 1: 2 2: 3 3: Object 4: function () {} 5: true 6: "hwllo" length: 7*/
看上去是一個類似陣列的資料結構,但是不是,就是 Set 資料結構常用方法和屬性size : 用來獲取該資料結構中有多少資料的
const s = new Set([1, 2, 3, {}, function () {}, true, 'hwllo'])console.log(s.size) // 7
看上去是一個和陣列資料型別差不多的資料結構,而且我們也看到了 length 屬性
但是不能使用,想要獲取該資料型別中的成員數量,需要使用 size 屬性
add : 用來向該資料型別中追加資料const s = new Set()s.add(0)s.add({})s.add(function () {})console.log(s.size) // 3
這個方法就是向該資料型別中追加資料使用的
delete : 是刪除該資料結構中的某一個數據const s = new Set()s.add(0)s.add({})s.add(function () {})s.delete(0)console.log(s.size) // 2
clear : 清空資料結構中的所有資料
const s = new Set()s.add(0)s.add({})s.add(function () {})s.clear()console.log(s.size) // 0
has : 查詢資料解構中有沒有某一個數據
const s = new Set()s.add(0)s.add({})s.add(function () {})console.log(s.has(0)) // true
forEach : 用來遍歷 Set 資料結構的方法
const s = new Set()s.add(0)s.add({})s.add(function () {})s.forEach(item => { console.log(item) // 0 {} function () {}})
方法介紹的差不多了,有一個問題出現了,那就是我們的方法要麼是新增,要麼是刪除,要麼是查詢,沒有獲取因為要獲取 Set 結構裡面的資料需要藉助一個 ... 展開運算子把他裡面的東西都放到一個數組裡面去,然後再獲取const s = new Set([1, 2, 3, 4, 5, 6])const a = [...s]console.log(a) // (6) [1, 2, 3, 4, 5, 6]console.log(a[0]) // 1console.log([...s][0]) // 1
又一個問題出現了,new 的時候需要以陣列的形式傳遞然後獲取的時候又要轉成陣列的形式獲取那麼我為什麼不一開始就定義陣列,要這個 Set 資料型別幹什麼這就不得不提到一個 Set 的特點Set 不允許儲存重複的資料
const s = new Set([1, 2, 3])s.add(4) // 此時 size 是 4s.add(1) // 此時 size 是 4s.add(2) // 此時 size 是 4s.add(3) // 此時 size 是 4
Map也是要和 new 連用是一個數據集合,是一個很類似於 物件 的資料集合
const m = new Map()console.log(m)/* Map(0) {} size: (...) __proto__: Map [[Entries]]: Array(0) length: 0*/
我們的物件中不管儲存什麼,key 一定是一個字串型別但是再 Map 裡面,我們的 key 可以為任意資料型別我們也管 Map 叫做 (值 = 值 的資料型別)const m = new Map([[{}, {}], [function () {}, function () {}], [true, 1]])console.log(m)/* Map(3) {{…} => {…}, ƒ => ƒ, true => 1} size: (...) __proto__: Map [[Entries]]: Array(3) 0: {Object => Object} key: {} value: {} 1: {function () {} => function () {}} key: ƒ () value: ƒ () 2: {true => 1} key: true value: 1 length: 3*/
常用方法和屬性size : 用來獲取該資料型別中資料的個數
const m = new Map([[{}, {}], [function () {}, function () {}], [true, 1]])console.log(m.size) // 3
delete : 用來刪除該資料集合中的某一個數據
const m = new Map([[{}, {}], [function () {}, function () {}], [true, 1]])m.delete(true)console.log(m.size) // 2
set : 用來向該資料集合中新增資料使用const m = new Map()m.set({ name: 'Jack' }, { age: 18 })console.log(m.size) // 1
get : 用來獲取該資料集合中的某一個數據
const m = new Map()m.set({ name: 'Jack' }, { age: 18 })m.set(true, function () {})console.log(m.get(true)) // function () {}
clear : 清除資料集合中的所有資料
const m = new Map()m.set({ name: 'Jack' }, { age: 18 })m.set(true, function () {})m.clear()console.log(m.size) // 0
has : 用來判斷資料集合中是否存在某一個數據
const m = new Map()m.set({ name: 'Jack' }, { age: 18 })m.set(true, function () {})console.log(m.has(true)) // true
最新評論