JS - 面向?qū)ο?- 屬性遍歷

對象屬性分類

對于屬性遍歷而言,可以將對象屬性分為是否可枚舉、是否為繼承 兩種

let ary = ['a', 'b', 'c']

ary 數(shù)組中,可枚舉屬性是對應(yīng)的索引 0, 1, 2 ,不可枚舉的是 length

對象屬性配置

對象中,屬性是否可枚舉可以通過 Object.defineProperty 設(shè)定

class Car {                                          // 創(chuàng)建類
  constructor(brand, model, color) {                
    this.brand = brand
    this.model = model
    this.color = color
  }
}

let mycar = new  Car('Tesla', 'model 3', 'red')     // 沒有的話 new 一個(gè)就好啦

Object.defineProperty(mycar ,"color",{
        value: "red",
        enumerable: false,       //是否可枚舉, 默認(rèn)值 false
        configurable: false,    //是否可配置,默認(rèn)值 false
        writable: false,        //沒有 writable 使用默認(rèn)值 false
  });

對象創(chuàng)建完成,在控制臺內(nèi)通過顏色可以判斷不可枚舉屬性,但作為一個(gè)嚴(yán)謹(jǐn)?shù)某绦騿T,當(dāng)然需要更科學(xué)的辦法啦

可枚舉屬性

Object.keys(o)

按順序遍歷返回一個(gè)數(shù)組,其包含對象 o 自身(不包括原型)的所有可枚舉屬性的名稱

Object.keys(mycar)          
// ["brand", "model"] 
for...in循環(huán)

該方法會依次訪問一個(gè)對象及其原型鏈中所有可枚舉的屬性,就當(dāng)前對象而言,效果較Object.keys(o) 相同

for (let i in my car) {
  console.log(i)
}
// brand
// model

但如果繼承的原型鏈上已有可枚舉屬性,原型上的 'foo' 也被遍歷進(jìn)來了

mycar.__proto__.foo = 'foo'

for (let i in mycar) {
  console.log(i)
}
// brand
// model
// foo

Object.keys(mycar)          
// ["brand", "model"] 

所以得再過濾下,使用 hasOwnProperty 過濾繼承屬性,返回布爾值

for(let i in mycar){
  // 此處可以使用 mycar.hasOwnProperty(i),
  // 以安全的角度看用 Object.prototype.hasOwnProperty.call(mycar,i) 
  if(Object.prototype.hasOwnProperty.call(mycar,i)){
    console.log(i)
  }
}
// brand
// model

所有屬性

Object.getOwnPropertyNames(o)

該方法返回一個(gè)數(shù)組,其包含對象 o 所有自有的屬性(無論是否可枚舉)的名稱

mycar.__proto__.foo = 'foo'

Object.getOwnPropertyNames( mycar )
// ["brand", "model", "color"]

不可枚舉屬性

那既然可枚舉和全部自有屬性都有辦法獲取,要獲取不可枚舉屬性就簡單了

mycar.__proto__.foo = 'foo'

Object.getOwnPropertyNames(mycar).filter(val =>
  !Object.keys(mycar).includes(val)
)
// ["color"]

遍歷順序

值得注意的是,Object.keys() 遍歷順序?qū)Σ煌瑢傩灶愋蜁r(shí),先后順序不同

let a = {'zz': 3, 3: 99, 1: 100, 'bb': 0}        
//["1", "3", "zz", "bb"]

引用 MDN 中說明:

一個(gè)對象的屬性名可以是任何有效的 JavaScript 字符串,或者可以被轉(zhuǎn)換為字符串的任何類型,包括空字符串

也就是說,對象的所有屬性都會通過轉(zhuǎn)換變化為字符串,而由數(shù)字轉(zhuǎn)過來字符串排序優(yōu)先(此處略有疑問)而 for...in循環(huán) 遍歷順序與 Object.keys() 一致

// 同時(shí)創(chuàng)建多個(gè)變量
let myObj = new Object(),
str = "myString",
rand = Math.random(),
obj = new Object(),
num1 = 23,
num2 = 99,
ary = [1,2];

myObj.type              = "Dot syntax";
myObj["date created"]   = "String with space";
myObj[str]              = "String value";
myObj[rand]             = "Random Number";
myObj[obj]              = "Object";
myObj[ary]              = 'here is a ary'
myObj[num2]             = 'here is a number_2'
myObj[""]               = "Even an empty string";
myObj[num1]             = 'here is a number_1'

for(let i in myObj){console.log(typeof i,' --- ', i, ' --- ',myObj[i])}
// 去下圖...

小結(jié)

  • 遍歷自有屬性:

    • 可枚舉:
      1. Object.keys(o) 遍歷 對象 o 上的所有可枚舉自有屬性
      2. for...in 遍歷對象 o 上所有自有屬性(包括繼承屬性)
    • 可枚舉 + 不可枚舉:
      1. Object.getOwnPropertyNames(o) 遍歷對象 o 上所有自有屬性(無論是否可枚舉)
    • 不可枚舉:
      1. 通過 Object.getOwnPropertyNames(o) 獲取所有自有屬性,在通過 Object.keys(mycar) 獲取 自有可枚舉屬性,在使用 filter 過濾
  • 遍歷順序:以屬性設(shè)定時(shí)順序?yàn)闇?zhǔn),數(shù)字例外優(yōu)先排序(僅參考)

  • 判斷是否屬于自有屬性(返回布爾值):
    1. 普通做法 mycar.hasOwnProperty(i)
    2. 更安全的做法 Object.prototype.hasOwnProperty.call(mycar,i)

統(tǒng)計(jì)表

源自 MDN ,關(guān)于屬性的 枚舉,繼承 統(tǒng)計(jì)表

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時(shí)請結(jié)合常識與多方信息審慎甄別。
平臺聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點(diǎn),簡書系信息發(fā)布平臺,僅提供信息存儲服務(wù)。

相關(guān)閱讀更多精彩內(nèi)容

  • 概要 64學(xué)時(shí) 3.5學(xué)分 章節(jié)安排 電子商務(wù)網(wǎng)站概況 HTML5+CSS3 JavaScript Node 電子...
    阿啊阿吖丁閱讀 9,851評論 0 3
  • ??面向?qū)ο螅∣bject-Oriented,OO)的語言有一個(gè)標(biāo)志,那就是它們都有類的概念,而通過類可以創(chuàng)建任意...
    霜天曉閱讀 2,261評論 0 6
  • 《日精進(jìn)打卡》 姓名:徐建蓉 公司名稱:寧波大發(fā)化纖有限公司 《幸福精進(jìn)》學(xué)習(xí)營第41期努力組 ...
    群_ff9f閱讀 512評論 0 1
  • 阿爸父, 我知道你的意思是好的, 這一切大不過你的愛, 可是, 我突然不會笑了, 主啊,懇求你, 將喜樂為我奪回。...
    輕小暖閱讀 817評論 1 3
  • 我真覺得活著讓我覺得好累,每次每次我想珍惜的東西都已經(jīng)在放棄我,而我卻后知后覺。感覺自己跟一個(gè)傻瓜一樣。 你...
    懷挺小姐閱讀 205評論 0 0

友情鏈接更多精彩內(nèi)容