您好,登錄后才能下訂單哦!
前言
JavaScript 是個(gè)很神奇的東西。但是 JavaScript中的一些東西確實(shí)很奇怪,讓人摸不著頭腦。其中之一就是當(dāng)你試圖訪問(wèn)嵌套對(duì)象時(shí),會(huì)遇到這個(gè)錯(cuò)誤
Cannot read property 'foo' of undefined
在大多數(shù)情況下,處理嵌套的對(duì)象,通常我們需要安全地訪問(wèn)最內(nèi)層嵌套的值。 來(lái)個(gè)粟子:
const user = { id: 101, email: 'jack@dev.com', personalInfo: { name: 'Jack', address: { line1: 'westwish st', line2: 'washmasher', city: 'wallas', state: 'WX' } } }
當(dāng)我們要訪問(wèn)user里面的name及city時(shí),我們會(huì)這樣寫。
const name = user.personalInfo.name; const userCity = user.personalInfo.address.city;
這是簡(jiǎn)單而直接的。
但是,由于某種原因,user 中的 personal不可用,對(duì)象結(jié)構(gòu)將是這樣的:
const user = { id: 101, email: 'jack@dev.com' }
現(xiàn)在,如果你在試著訪問(wèn) name ,將會(huì)得到一個(gè) Cannot read property 'name' of undefined 的錯(cuò)誤。
const name = user.personalInfo.name; // Cannot read property 'name' of undefined
這是因?yàn)槲覀冊(cè)噲D訪問(wèn)對(duì)象中不在的 key 為 name 的屬性。
大多數(shù)開發(fā)人員處理這種情況的常用方法如下,
const name = user && user.personalInfo ? user.personalInfo.name : null;
如果你的嵌套結(jié)構(gòu)很簡(jiǎn)單,這是可以的,但是如果數(shù)據(jù)嵌套五或六層深,那么你的代碼就會(huì)看起很混亂:
let city; if ( data && data.user && data.user.personalInfo && data.user.personalInfo.addressDetails && data.user.personalInfo.addressDetails.primaryAddress ) { city = data.user.personalInfo.addressDetails.primaryAddress; }
有一些技巧可以處理這種混亂的對(duì)象結(jié)構(gòu)。
Oliver Steele的嵌套對(duì)象訪問(wèn)模式
這是我個(gè)人的最愛,因?yàn)樗勾a看起來(lái)干凈簡(jiǎn)單。 我從 stackoverflow 中選擇了這種風(fēng)格,一旦你理解它是如何工作的,它就非常吸引人了。
const name = ((user || {}).personalInfo || {}).name;
使用這種表示法,永遠(yuǎn)不會(huì)遇到無(wú)法讀取未定義的屬性“name”。做法是檢查用戶是否存在,如果不存在,就創(chuàng)建一個(gè)空對(duì)象,這樣,下一個(gè)級(jí)別的鍵將始終從存在的對(duì)象訪問(wèn)。
不幸的是,你不能使用此技巧訪問(wèn)嵌套數(shù)組。
使用數(shù)組Reduce訪問(wèn)嵌套對(duì)象
Array reduce 方法非常強(qiáng)大,可用于安全地訪問(wèn)嵌套對(duì)象。
const getNestedObject = (nestedObj, pathArr) => { return pathArr.reduce((obj, key) => (obj && obj[key] !== 'undefined') ? obj[key] : null, nestedObj); } // 將對(duì)象結(jié)構(gòu)作為數(shù)組元素傳入 const name = getNestedObject(user, ['personalInfo', 'name']); // 要訪問(wèn)嵌套數(shù)組,只需將數(shù)組索引作為數(shù)組元素傳入。. const city = getNestedObject(user, ['personalInfo', 'addresses', 0, 'city']); // 這將從 addresses 中的第一層返回 city
Typy
如果你認(rèn)為上面的方法太過(guò)非主流,那么可以使用 Typy庫(kù)。除了安全訪問(wèn)嵌套對(duì)象之外,它還可以做很多很棒的事情。
如果使用Typy,代碼將如下所示
import t from 'typy'; const name = t(user, 'personalInfo.name').safeObject; const city = t(user, 'personalInfo.addresses[0].city').safeObject; // address is an array
這里還有一些其他的庫(kù),如 Lodash 和 Ramda,可以做到這一點(diǎn)。但是在輕量級(jí)前端項(xiàng)目中,特別是如果你只需要這些庫(kù)中的一兩個(gè)方法時(shí),最好選擇另一個(gè)輕量級(jí)庫(kù),或者編寫自己的庫(kù)。
總結(jié)
以上就是這篇文章的全部?jī)?nèi)容了,希望本文的內(nèi)容對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,謝謝大家對(duì)億速云的支持。
免責(zé)聲明:本站發(fā)布的內(nèi)容(圖片、視頻和文字)以原創(chuàng)、轉(zhuǎn)載和分享為主,文章觀點(diǎn)不代表本網(wǎng)站立場(chǎng),如果涉及侵權(quán)請(qǐng)聯(lián)系站長(zhǎng)郵箱:is@yisu.com進(jìn)行舉報(bào),并提供相關(guān)證據(jù),一經(jīng)查實(shí),將立刻刪除涉嫌侵權(quán)內(nèi)容。