標簽: ES6
- ES6允許按照一定模式,從數(shù)組和對象中提取值,對變量進行賦值
- 本質上屬于“模式匹配”,只要等號兩邊模式相同异吻,左邊的變量就會被賦予相應的值
數(shù)組的解構賦值
基本用法
var [a, b, c] = [1, 2, 3]
a // 1
b // 2
c // 3
- 解構不成功,則解構不成功的變量的值為undefined
- 不完全解構喜庞,即等號左邊的模式只匹配等號右邊數(shù)組的一部分诀浪,則解構依然成功
let [x, y] = [1, 2, 3]
x // 1
y // 2
對于數(shù)組解構賦值,如果等式右邊不是可遍歷結構(本身 / 轉化后的對象具備Iterator接口),將會報錯
// 報錯延都,轉化后的對象不具備Iterator接口
let [a] = 1
let [b] = false
// 報錯雷猪,對象本身不具備Iterator接口
let [c] = {}
// 解構成功,字符串能轉換成類似數(shù)組的對象
let [d, e, f, g, h] = 'hello'
默認值
- 解構允許指定默認值
var [x, y = 2] = [1] // x=1晰房,y=2
- 使用嚴格相等運算符(===)判斷一個位置是否有值求摇,僅在嚴格等于undefined時射沟,默認值生效
var [x = 1] = [undefined] // x=1
var [y = 1] = [null] // y=null,默認值不生效
由于`(null===undefined)`的值為false与境,所以默認值不生效验夯,`y`的值為null
- 如果默認值為一個表達式,那么這個表達式是惰性求值的摔刁,只有用到的時候才會求值
function f() {
console.log(123)
}
let [x = f()] = [1] // 無輸出
- 默認值可以引用解構賦值的其他變量挥转,但該變量必須已經聲明
let [x = 1, y = x] = [] // x=1,y=1
let [a = b, b = 1] = [] // 報錯
對象的解構賦值
基本用法
var { foo, bar } = { foo: 123, bar: 345 }
foo // 123
bar // 345
- 數(shù)組解構共屈,變量的取值取決于它的位置
- 對象解構,變量必須與屬性同名借宵,才能得到正確的值
var { abc } = { foo: 123, bar: 345 }
abc // undefined
對象的解構賦值實際上是以下形式的簡寫
var { foo, bar } = { foo: 123, bar: 345 } // 簡寫
var { foo: foo, bar: bar } = { foo: 123, bar: 345 }
對象解構賦值的內部機制暇务,是先找到同名屬性怔软,然后再賦給相應的變量挡逼。
真正被賦值的是后者腻豌,而不是前者
var { foo: baz } = { foo: 123, bar: 345 }
baz // 123
foo // Error:foo is not defined
對一個已經聲明的變量解構賦值吝梅,不能將大括號 { } 寫在行首,避免 javascript 將其解析為代碼塊
var x
({ x } = { x: 1 }) // 正確寫法
{ x } = { x: 1 } // 錯誤寫法
默認值
默認值生效的條件是做瞪,對象的屬性嚴格等于undefined
var { message: msg = 123, x } = { message: undefined, x: null }
msg // 123
x // null
解構嵌套結構的對象
var node = {
loc: {
start: {
line: 1,
column: 5
}
}
}
var { loc: { start: { line, column } } } = node
line // 1
column // 5
loc // Error
start // Error
注意:loc 和 start 是模式装蓬,不是變量牍帚,因此不會被賦值
解構對象是嵌套的對象乳蛾,而且子對象所在的父對象不存在鄙币,會報錯
var { foo: { bar } } = {}
foo
為父對象蹂随,bar
為子對象,foo
不存在详幽,報錯
原因很簡單:foo
這時為undefined
浸锨,再取子屬性bar
就會報錯
其他類型的解構賦值
字符串的解構賦值
字符串可以解構賦值,此時字符串被轉換成了一個類似數(shù)組的對象
let [d, e, f, g, h] = 'hello'
var { length: len } = 'hello'
len // 5
數(shù)值和布爾值的解構賦值
解構賦值時迟郎,如果等號右邊是數(shù)值或布爾值宪肖,則先轉為對象
undefined
和null
無法轉為對象控乾,會報錯
let { toString: s } = 123
s === Number.prototype.toString // true
let { toString: s } = true
s === Boolean.prototype.toString // true
函數(shù)參數(shù)的解構賦值
function add([x, y]) {
return x + y
}
add([1, 2]) // 3
注意區(qū)分以下兩種情況:
function move({ x = 0, y = 0 } = {}) {
return [x, y]
}
move({ x: 3, y: 1 }) // { x: 3, y: 1 }
move({ x: 3}) // { x: 3, y: 0 }
move({}) // { x: 0, y: 0 }
move() // { x: 0, y: 0 }
為解構設置默認值蜕衡,當解構失敗時使用默認值
move()
使用了函數(shù)默認值{}
慨仿,然后解構镰吆,解構失敗跑慕,使用解構默認值
function move({} = { x = 0, y = 0 }) {
return [x, y]
}
move({ x: 3, y: 1 }) // { x: 3, y: 1 }
move({ x: 3}) // { x: 3, y: undefined }
move({}) // { x: undefined, y: undefined }
move() // { x: 0, y: 0 }
為函數(shù)設置默認值,僅當函數(shù)沒有傳參的時候才使用默認值
move({})
傳入了空對象相赁,所以沒有使用函數(shù)默認值{}
钮科,接下來是解構绵脯,解構失敗休里,由于沒有解構默認值赃承,其值為undefined
變量解構的用途
交換變量的值
[x, y] = [y, x]
從函數(shù)返回多個值
function example() {
return [1, 2, 3]
}
var [a, b, c] = example()
function example() {
return {
foo: 1,
bar: 2
}
}
var { foo, bar } = example()
函數(shù)參數(shù)的定義
// 參數(shù)是一組有次序的值
function f([x, y, z]) { ... }
f([1, 2, 3])
// 參數(shù)是一組無次序值
function f({ x, y, z }) { ... }
f({ z: 1, y: 2, x: 3 })
提取JSON數(shù)據(jù)
var jsonData = {
id: 1,
is_error: false,
result: [123, 456]
}
let { id, is_error, result } = jsonData
函數(shù)參數(shù)的默認值
jQuery.ajax = function(url, {
async = true,
beforeSend = function() {},
cache = true,
complete = function() {},
corssDomain = false,
global = true
// ... more config
}) {
// ... do stuff
}
遍歷Map結構
任何部署了 Iterator接口的對象,都可以用 for...of 循環(huán)遍歷
var map = new Map()
map.set('first', 'hello')
map.set('second', 'world')
for (let [key, value] of map) {
console.log(key, value)
}
// first hello
// second world
輸出模塊的指定方法
const { SourceMapConsumer, SourceNode } = require("source-map")