ES項(xiàng)目學(xué)習(xí)筆記(三)賦值操作更簡便 解構(gòu)賦值

用一個(gè)經(jīng)常遇到的問題來說明這一賦值的好處之一漏策,對兩個(gè)變量的值進(jìn)行替換膀估,通常我們得另外聲明一個(gè)變量來作為兩個(gè)變量交換的媒介舀寓,而現(xiàn)在如下代碼就可以解決:

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

解構(gòu)賦值上述的用法是對數(shù)組的解構(gòu)賦值,總的來說結(jié)構(gòu)賦值大致可以分為數(shù)組解構(gòu)賦值怒允,對象解構(gòu)賦值字符解構(gòu)賦值识虚,數(shù)值和布爾解構(gòu)賦值肢扯,函數(shù)參數(shù)解構(gòu)賦值妒茬。

無論何種解構(gòu)賦值担锤,解構(gòu)賦值表達(dá)式的左邊部分,即解構(gòu)的目標(biāo)乍钻,而右邊的值肛循,即左邊解構(gòu)的源,都遵循一個(gè)左右互相匹配的規(guī)則银择,只要等號兩邊的模式相同多糠,左邊的變量就會(huì)被賦予對應(yīng)的值。

數(shù)組解構(gòu)賦值

上述的代碼就是數(shù)組解構(gòu)賦值的基本用法浩考。以下是數(shù)組解構(gòu)賦值的其它使用方式

//嵌套
{
  let [a, [[b], c]] = [1, [[2], 3]];
  console.log(a,b,c); //1,2,3
}
//可忽略
{
  let [a, , b] = [1, 2, 3];
  console.log(a,b);
}
//剩余運(yùn)算符
{
  let a,b,rest;
  [a,b,...rest] = [1,2,3,4,5,6];
  console.log(a,b,rest); //1,2,[4,5,6]
}
//不完全解構(gòu)
{
    let [a,b] = [1,2,3];
}

上述的變量全都可以成功賦值夹孔,也就是成功解構(gòu),但也有無法解構(gòu)成功的析孽,比如:

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

當(dāng)解構(gòu)目標(biāo)在解構(gòu)的源對應(yīng)位置找不到值,則無法成功解構(gòu),變量的值就會(huì)變成undefined,...剩余運(yùn)算符的變量為[].
在實(shí)際開發(fā)場景中返回的值可能有多種情況,可能你想要的值在某個(gè)位置確實(shí)沒有,那么還可以使用默認(rèn)值搭伤。

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

ES6 內(nèi)部使用嚴(yán)格相等運(yùn)算符(===),判斷一個(gè)位置是否有值袜瞬。只有當(dāng)一個(gè)數(shù)組成員嚴(yán)格等于undefined怜俐,默認(rèn)值才會(huì)生效
默認(rèn)值可以引用解構(gòu)賦值的其他變量,但該變量必須已經(jīng)聲明邓尤。

let [a = 1, b = a] = [];     // a=1; b=1
let [a = 1, b = a] = [2];    // a=2; b=2
let [a = 1, b = a] = [1, 2]; // a=1; b=2
let [a = b, b = 1] = [];     // ReferenceError: b is not defined

如果解構(gòu)的源不是數(shù)組拍鲤,就會(huì)報(bào)錯(cuò)

let [foo] = 1;
let [foo] = false;
let [foo] = NaN;
let [foo] = undefined;
let [foo] = null;
let [foo] = {};

對象解構(gòu)賦值

對象解構(gòu)賦值同樣遵循左右互相匹配的規(guī)則,類似數(shù)組一樣有嵌套汞扎,默認(rèn)值等季稳,但要注意的是變量名稱需要和對象中的屬性值要對應(yīng),因?yàn)閿?shù)組的位置相對應(yīng)來說是有序的澈魄,而對象中是無序的景鼠,只能通過屬性來作為位置查找。如果要使用其它的變量名稱一忱,可以使用:重新指定變量名稱莲蜘,注意此時(shí)引用地址已被新變量接收,:左邊的變量就沒有地址了,再訪問的話是空的帘营,是真的輸出為空的字符票渠,在下面示例代碼中有對應(yīng)的寫法:

//基本
{
  let {a,b} = {a:1,b:2}
  console.log(a,b);
  let {name:newName} = {name:'tony'}
  console.log(name)//''
  console.log(newName)//tony
}
//默認(rèn)值
{
  let {x = 3} = {};
  let {a,b = 2}={a:1};
}
//嵌套
{
  const obj = {
    name:{
      chinese_name:{
        first_name:'Chen',
        last_name:'chuhai'
      },
      english_name:{
        first_name:'Chen',
        last_name:'tony'
      }
    }
  };
  let {name,name:{chinese_name},name:{chinese_name:{last_name:my_name}}} = obj;
  console.log(name);//{chinese_name: {...},english_name: {...}}
  console.log(chinese_name);//{first_name: "Chen",last_name: "chuhai"}
  console.log(my_name)//chuhai
}

和數(shù)組一樣,對象解構(gòu)也有嵌套芬迄,只是這個(gè)嵌套容易讓人犯暈聘萨,別怕,回顧著之前講的死姚,一層層剝析濒持。
先看解構(gòu)賦值的左邊,前面說了叫做解構(gòu)的目標(biāo)尖坤,第一個(gè)為name變量,這個(gè)很簡單了,這個(gè)就對應(yīng)著右邊解構(gòu)源叫做name的屬性值蚀腿,然后是第二個(gè)解構(gòu)目標(biāo),根據(jù)左右匹配的規(guī)則扫外,可以得出chinese_name就是右邊解構(gòu)源name屬性值對象中chinese_name的屬性值莉钙,最后第三個(gè),last_name就是對應(yīng)結(jié)構(gòu)源上"chuhai"這個(gè)值了筛谚,只是用:重新指定了變量的名稱為my_name磁玉。
結(jié)構(gòu)目標(biāo)最后只有一個(gè),即得出最后的變量只有一個(gè)驾讲,第二次和第三次過程中分別出現(xiàn)的name和chinese_name蚊伞,只是得到解構(gòu)目標(biāo)過程中為了和解構(gòu)源相匹配而出現(xiàn)的,這樣說應(yīng)該就能解決大部分人對在解構(gòu)目標(biāo)出現(xiàn)的多個(gè)變量的迷惑了(可能只是我剛一接觸時(shí)有這種迷惑)吮铭,那些不是最終的變量时迫,而是為了匹配解構(gòu)源對應(yīng)位置的

解構(gòu)賦值也并不是一定需要聲明變量來賦值的,還可以通過下面的方式進(jìn)行賦值

let obj = {};
let arr = [];
({ foo: obj.prop, bar: arr[0] } = { foo: 123, bar: true });
obj // {prop:123}
arr // [true]

代碼很容易看明白沐兵,拋出一個(gè)注意點(diǎn)别垮,解構(gòu)賦值的表達(dá)式用了一個(gè)括號,為什么呢扎谎?
因?yàn)椴荒敲磳憰?huì)報(bào)錯(cuò)碳想。解構(gòu)賦值用的變量在之前有聲明過,而{}恰好會(huì)被作為代碼塊理解,這樣上下文出現(xiàn)兩個(gè)相同名稱的變量解析時(shí)就會(huì)報(bào)錯(cuò)毁靶,放在一個(gè)圓括號里面胧奔,就可以正確執(zhí)行。詳細(xì)原因請大家看大神阮一峰e(cuò)s6入門--圓括號問題
對象解構(gòu)賦值和數(shù)組差不多预吆,有沒有獨(dú)特一點(diǎn)的龙填?
有的,對象的解構(gòu)賦值還可以拿到繼承的屬性拐叉,然后數(shù)組是特殊的對象岩遗,其實(shí)也能用對象解構(gòu)的方式來解構(gòu)數(shù)組。上代碼

//繼承
const obj1 = {};
const obj2 = { foo: 'bar' };
Object.setPrototypeOf(obj1, obj2);
const { foo } = obj1;// "bar"
//數(shù)組解構(gòu)
let arr = [1, 2, 3];
let {0 : first, [arr.length - 1] : last} = arr;
first // 1
last // 3

字符串的解構(gòu)賦值

后面的幾種解構(gòu)賦值基本上也是從對象解構(gòu)或者數(shù)組解構(gòu)延伸出來的凤瘦,字符串可以看成一個(gè)被分割為數(shù)組的對象宿礁,所以,可以這么用
{
//作為數(shù)組
let [a,b,c,d] = 'tony';
console.log(a,b,c,d);//t o n y
//作為對象解構(gòu)還能這么用
let {length} = 'tony';
console.log(length);//4
}

數(shù)值和布爾解構(gòu)賦值

解構(gòu)賦值按照左右匹配規(guī)則來說蔬芥,只要解構(gòu)的源有數(shù)值梆靖,有結(jié)構(gòu)控汉,那么都可以進(jìn)行解構(gòu),關(guān)鍵是看以什么解構(gòu)規(guī)則進(jìn)行解構(gòu)返吻,除去上面的數(shù)組對象字符串姑子,其它的只要能轉(zhuǎn)成對象,有結(jié)構(gòu)测僵,有數(shù)值街佑,就可以進(jìn)行解構(gòu),像undefinednull沒值沒結(jié)構(gòu)的恨课,就無法進(jìn)行解構(gòu)了舆乔,而布爾和數(shù)值可以岳服。
{
//轉(zhuǎn)為對象后繼承了字符對象的toString方法
let {toString: s} = 123;
s === Number.prototype.toString // true
let {toString: s} = true;
s === Boolean.prototype.toString // true
}

函數(shù)參數(shù)解構(gòu)賦值

這部分函數(shù)解構(gòu)賦值并不是簡單的這樣

{
  function f(){
    return [1,2]
  }
  let a,b;
  [a,b]=f();
  console.log(a,b);
}

這樣實(shí)際是拿函數(shù)的執(zhí)行結(jié)果來進(jìn)行解構(gòu)賦值太小兒科剂公,我也曾想過為什么不能是{} = f這樣的解構(gòu)賦值,方法里面雖然有結(jié)構(gòu)有內(nèi)容吊宋,但是纲辽,誰能告訴怎么個(gè)一一對應(yīng)法,這不可能璃搜,所以拖吼,只能拿方法的傳參講講了。

{
  function add([a, b]){
    return a + b;
  }
  console.log(add([1, 2])) // 3
  console.log([[1, 2], [3, 4]].map(([a, b]) => a + b)) //[3,7];
}

在傳參的過程中進(jìn)行解構(gòu)賦值这吻,原理和前面講的解構(gòu)賦值是一樣的吊档。

至此結(jié)構(gòu)賦值的類型都說完了,回到最初說明這一運(yùn)算的用途唾糯,除了交換變量怠硼,還有其它的用途,在此一一列舉:
至此結(jié)構(gòu)賦值的類型都說完了移怯,回到最初說明這一運(yùn)算的用途香璃,除了交換變量,還有其它的用途舟误,在此一一列舉:

  • 交換變量
  • 處理函數(shù)返回值(見上述函數(shù)參數(shù)解構(gòu)賦值的第一段代碼)
  • 處理函數(shù)傳參(還是見上述函數(shù)參數(shù)解構(gòu)賦值的代碼)
  • 處理JSON數(shù)據(jù)
  • 函數(shù)參數(shù)的默認(rèn)值
  • 遍歷 Map 結(jié)構(gòu)
  • 引入模塊的指定方法
  import { loginHtml, loginResultPage, userWxBinding, consolidatedAccountContent} from '../../html/login';

以上為解構(gòu)賦值的筆記內(nèi)容葡秒,如有補(bǔ)充和需探討的,歡迎留言評論~

?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
  • 序言:七十年代末嵌溢,一起剝皮案震驚了整個(gè)濱河市眯牧,隨后出現(xiàn)的幾起案子,更是在濱河造成了極大的恐慌赖草,老刑警劉巖学少,帶你破解...
    沈念sama閱讀 221,198評論 6 514
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件,死亡現(xiàn)場離奇詭異疚顷,居然都是意外死亡旱易,警方通過查閱死者的電腦和手機(jī)禁偎,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 94,334評論 3 398
  • 文/潘曉璐 我一進(jìn)店門,熙熙樓的掌柜王于貴愁眉苦臉地迎上來阀坏,“玉大人如暖,你說我怎么就攤上這事〖商茫” “怎么了盒至?”我有些...
    開封第一講書人閱讀 167,643評論 0 360
  • 文/不壞的土叔 我叫張陵,是天一觀的道長士修。 經(jīng)常有香客問我枷遂,道長,這世上最難降的妖魔是什么棋嘲? 我笑而不...
    開封第一講書人閱讀 59,495評論 1 296
  • 正文 為了忘掉前任酒唉,我火速辦了婚禮,結(jié)果婚禮上沸移,老公的妹妹穿的比我還像新娘痪伦。我一直安慰自己,他們只是感情好雹锣,可當(dāng)我...
    茶點(diǎn)故事閱讀 68,502評論 6 397
  • 文/花漫 我一把揭開白布网沾。 她就那樣靜靜地躺著,像睡著了一般蕊爵。 火紅的嫁衣襯著肌膚如雪辉哥。 梳的紋絲不亂的頭發(fā)上,一...
    開封第一講書人閱讀 52,156評論 1 308
  • 那天攒射,我揣著相機(jī)與錄音醋旦,去河邊找鬼。 笑死匆篓,一個(gè)胖子當(dāng)著我的面吹牛浑度,可吹牛的內(nèi)容都是我干的。 我是一名探鬼主播鸦概,決...
    沈念sama閱讀 40,743評論 3 421
  • 文/蒼蘭香墨 我猛地睜開眼箩张,長吁一口氣:“原來是場噩夢啊……” “哼!你這毒婦竟也來了窗市?” 一聲冷哼從身側(cè)響起先慷,我...
    開封第一講書人閱讀 39,659評論 0 276
  • 序言:老撾萬榮一對情侶失蹤,失蹤者是張志新(化名)和其女友劉穎咨察,沒想到半個(gè)月后论熙,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體,經(jīng)...
    沈念sama閱讀 46,200評論 1 319
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡摄狱,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 38,282評論 3 340
  • 正文 我和宋清朗相戀三年脓诡,在試婚紗的時(shí)候發(fā)現(xiàn)自己被綠了无午。 大學(xué)時(shí)的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片。...
    茶點(diǎn)故事閱讀 40,424評論 1 352
  • 序言:一個(gè)原本活蹦亂跳的男人離奇死亡祝谚,死狀恐怖宪迟,靈堂內(nèi)的尸體忽然破棺而出,到底是詐尸還是另有隱情交惯,我是刑警寧澤次泽,帶...
    沈念sama閱讀 36,107評論 5 349
  • 正文 年R本政府宣布,位于F島的核電站席爽,受9級特大地震影響意荤,放射性物質(zhì)發(fā)生泄漏。R本人自食惡果不足惜只锻,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 41,789評論 3 333
  • 文/蒙蒙 一玖像、第九天 我趴在偏房一處隱蔽的房頂上張望。 院中可真熱鬧炬藤,春花似錦御铃、人聲如沸。這莊子的主人今日做“春日...
    開封第一講書人閱讀 32,264評論 0 23
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽咬腋。三九已至羹膳,卻和暖如春,著一層夾襖步出監(jiān)牢的瞬間根竿,已是汗流浹背陵像。 一陣腳步聲響...
    開封第一講書人閱讀 33,390評論 1 271
  • 我被黑心中介騙來泰國打工, 沒想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留寇壳,地道東北人醒颖。 一個(gè)月前我還...
    沈念sama閱讀 48,798評論 3 376
  • 正文 我出身青樓,卻偏偏與公主長得像壳炎,于是被迫代替她去往敵國和親泞歉。 傳聞我的和親對象是個(gè)殘疾皇子,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 45,435評論 2 359

推薦閱讀更多精彩內(nèi)容