1. 程式人生 > 程式設計 >詳解JS ES6變數的解構賦值

詳解JS ES6變數的解構賦值

1.什麼是解構?

ES6允許按照一定模式,從陣列和物件中提取值,對變數進行賦值,這被稱為解構。它在語法上比ES5所提供的更加簡潔、緊湊、清晰。它不僅能減少你的程式碼量,還能從根本上改變你的編碼方式。

2.陣列解構

以前,為變數賦值,我們只能直接指定值,比如

let a = 1;
let b = 2; 
let c = 3;

現在可以用陣列解構的方式來進行賦值

let [a,b,c] = [1,2,3];
console.log(a,c); // 1,3

這是陣列解構最基本型別的用法,還可以解構物件陣列

// 物件陣列解構
let [a,c] = [{name: 'jacky'},{name: 'monkey'},{name: 'houge'}];
console.log(a,c); // {name: 'jacky'},{name: 'houge'}

3.陣列模式和賦值模式統一

這條可以理解為等號左邊和等號右邊的形式要統一,如果不統一解構將失敗。

let [a,[b,c],d] = [1,[2,3],4];
console.log(a,c,d); // 1 2 3 4

 // 提取除第二、三個外的所有數值
let [a,3,d); //1 4
    
let [a,...b] = [1,b); // 1 [2,4]
        
let [a,...d] = [1,4,5];
console.log(a,d); // 1 [4,5]
如果解構不成功,變數的值就等於undefined

let [a,c] = [2,c); // 2 3 undefined

let [c] = [];
console.log(c); // undefined

如果解構不成功,變數的值就等於undefined

let [a,c); // 2 3 undefined

let [c] = [];
console.log(c); // undefined

上述是完全解構的情況,還有一種是不完全解構,即iIaQGx等號左邊的模式,只匹配一部分的等號右邊的陣列,解構依然可以成功。

let [x,y] = [1,3]; 
console.log(x,y); // 1 2

let [a,[b],d); // 1 2 4

4.解構的預設值

解構賦值允許指定預設值。

let [a,b=2] = [1];
console.log(a,b); // 1 2

let [a=1,b=2,d=13] = [10,11,12];
console
程式設計客棧
.log(a,d); // 10 11 12 13

5.物件的解構賦值

物件的解構與陣列有一個重要的不同。陣列的元素是按次序排列的,變數的取值由它的位置決定;而物件的屬性沒有次序,變數必須與屬性同名,才能取到正確的值。

// 物件解構賦值的內部機制,是先找到同名屬性,然後再賦給對應的變數。真正被賦值的是後者,而非前者。
let obj = { a: "aaa",b: "bbb" };
let { a: x,b: y } = obj; 
console.log(x,y); // aaa bwww.cppcns.combb

let { a,b } = { a: 'aaa',b: 'bbb' };
console.log(a,b); // aaa bbb

// 不按照順序
let { b,a } = { a: 'test1',b: 'test2' }
console.log(a,b) // test1 test2


// 巢狀解構
let { obj: { name }} = { obj: { name: 'jacky',age: '22' } }
console.log(name) // jacky

// 稍微複雜的巢狀
let obj = {
    p: [
        'Hello',{ y: 'World' }
    ]
};

let { p: [x,{ y }] } = obj;
console.log(x,y); // Hello World

如果變數名與屬性名不一致,必須寫成下面http://www.cppcns.com這樣。

var { foo: rename } = { foo: "aaa",bar: "bbb" };
console.log(rename); // aaa
console.log(foo); // Uncaught ReferenceError: foo is not defined

如果在解構之前就定義了變數,這時候再解構會出現問題。下面是錯誤的程式碼,編譯會報錯(因為js引擎會將{a}理解成一個程式碼塊,從而發生語法錯誤。只有不將大括號寫在行首,避免js將其解釋成程式碼塊,才能解決這個問題)

let a;
let obj = { a: "aaa" };
{a} = obj; // Uncaught SyntaxError: Unexpected token '='

要解決報錯,使程式正常,這時候只要在解構的語句外邊加一個圓括號就可以了

let a;
let obj = { a: "aaa" };
( {a} = obj );
console.log(a); // aaa

6.函式引數

函式的引數也可以使用解構賦值。

function add([x,y]){
  return x + y;
}

add([1,2]); // 3

函式引數的解構也可以使用預設值。

function fn(x,y = 7) {
    return x + y;
}
console.log(fn(3)); // 10

7.字串解構

字串被轉換成了一個類似陣列的物件。

const [a,d,e,f] = "hello";
console.log(a); //h
console.log(b); //e
console.log(c); //l
console.log(d); //l
console.log(e); //o
console.log(f); //undefined

8.數值和布林值的解構賦值

解構賦值時,如果等號右邊是數值和布林值,則會先轉為物件。

let {toString: s} = 0;
console.log(s === Number.prototype.toString); // true

let {toString: s} = true;
console.log(s === Boolean.prototype.toString); // true

解構賦值的規則是,只要等號右邊的值不是物件或陣列,就先將其轉為物件。由於undefined和null無法轉為物件,所以對它們進行解構賦值,都會報錯

let { prop: x } = undefined; // TypeError
let { prop: y } = null; // TypeError

9.解構賦值的應用

1.交換變數的值

通常交換兩個變數的方法需要一個額外的臨時變數,如下

let a = 1;
let b = 2;
let temp;

temp = a;
a = b;
b = temp;

console.log(a,b); // 2 1

用ES6解構賦值的話,會變得很簡潔

let a = 1;
let b = 2;
[a,b] = [b,a];

console.log(a,b); // 2 1

2.從函式返回多個值

函式只能返回一個值,如果要返回多個值,只能將它們放在陣列或物件裡返回。有了解構賦值,取出這些值就非常方便。

// 返回一個數組
function example() {
  return [1,3];
}
let [a,c] = example();

// 返回一個物件
function example() {
  return {
    foo: 1,bar: 2
  };
}
let { foo,bar } = example();

3.訪問陣列中元素

有種場景,比如有一個數組(可能為空)。並且希望訪問陣列的第一個、第二個或第n個項,但如果該項不存在,則使用指定預設值。

通常會使用陣列的length屬性來判斷

const list = [];

let firstItem = 'hello';
if (list.length > 0) {
    firstItem = list[0];
}

console.log(firstItem); // hello

如果用ES6解構賦值來實現上述邏輯

const list = [];
const [firstItem = 'hello'] = list;

console.log(firstItem); // 'hello'

4.提取 JSON資料

let jsonData = {
  id: 42,status: "OK",iIaQGx
  data: [867,5309]
};

let { id,status,data: number } = jsonData;

console.log(id,number);
// 42,"OK",[867,5309]

5.遍歷 Map 結構

任何部署了 Iterator 介面的物件,都可以用for...of迴圈遍歷。Map 結構原生支援 Iterator 介面,配合變數的解構賦值,獲取鍵名和鍵值就非常方便。

const map = new Map();
map.set('first','hello');
map.set('second','world');

for (let [key,value] of map) {
  console.log(key + " is " + value);
}
// first is hello
// second is world

如果只想獲取鍵名,或者只想獲取鍵值,可以寫成下面這樣。

// 獲取鍵名
for (let [key] of map) {
  // ...
}

// 獲取鍵值
for (let [,value] of map) {
  // ...
}

以上就是詳解JS ES6變數的解構賦值的詳細內容,更多關於JS ES6變數解構賦值的資料請關注我們其它相關文章!