一直以來對象的術語描述沒有統一的标準,于是ES6規範定義了每一個類别的對象,對象的類别如下:
1、普通(Ordinary)對象
具有JS對象所有的預設内部行為
2、特異(Exotic)對象
具有某些與預設行為不符的内部行為
3、标準(Standard)對象
ES6規範中定義的對象,例如,Array、Date等。标準對象既可以是普通對象,也可以是特異對象
4、内建對象
腳本開始執行時存在于JS執行環境中的對象,所有标準對象都是内建對象
當一個對象的屬性與本地變量同名時,隻寫屬性名即可
對象的方法也可以簡寫,消除了冒号和function關鍵字
兩者的唯一差別是,簡寫方法可以使用super關鍵字,普通方法不可以
在ES5中是無法為對象字面量定義可計算屬性名的,比如說屬性名是一個變量。但在ES6中可以通過為屬性名加一對方括号來定義可計算屬性名。
在JS中,判斷兩個值是否相等,通常會使用相等運算符或全等運算符,但是有時候即使使用全等運算符也不一定完全靠得住
ES6引入了<code>Object.is()</code>方法來彌補全等運算符的不準确運算。這個方法接受兩個參數,如果這兩個參數類型相等且具有相同的值,則傳回true,否則傳回false
ES6新增了Object.assign()方法用于對象合并,該方法的第一個參數是目标對象,後面的參數是源對象,源對象的數量不限。
Object.assign()方法可以把源對象按照順序将屬性複制到目标對象中,如果目标對象與源對象有同名屬性,或者源對象與源對象有同名屬性,那麼後面的屬性會覆寫前面的屬性。
注意: 屬性的複制實際上是淺拷貝的過程,并且隻拷貝源對象自身的屬性,對于繼承屬性和不可枚舉屬性是不拷貝的
在ES6中,無論是在嚴格模式還是非嚴格模式下,代碼不再檢查重複屬性,對于每一組重複屬性,都會選取最後一個取值
如果是在ES5嚴格模式下,當同時存在多個同名屬性時會抛出錯誤
ES6嚴格規定了對象的自有屬性被枚舉時的傳回順序,這會影響到Object.getOwnPropertyNames()方法及Reflect.ownKeys傳回屬性的方式,自有屬性枚舉順序的基本規則如下:
1、所有數字鍵按升序排序
2、所有字元串鍵按照它們被加入對象的順序排序
3、所有symbol鍵按照它們被加入對象的順序排序
<code>__proto__</code>屬性,用來讀取或設定目前對象的prototype對象,目前所有浏覽器都部署了該屬性。
标準規定,隻有浏覽器必須部署<code>__proto__</code>屬性。開發過程中最好不要直接使用該屬性,而是使用Object.setPrototypeOf()(寫操作)、Object.getPrototypeOf()(讀操作)、Object.create()(生成操作)來代替
Object.getPrototypeOf(obj)方法用于擷取一個對象的原型對象
Object.setPrototypeOf()方法與proto作用相同,可以改變任意指定對象的原型。該方法接收兩個參數:要改變原型的對象和替代第一個參數原型的對象
對象原型的真實值被儲存在内部專用屬性[[protơtype]]中,調用Object.getPrototypeOf()方法傳回儲存在其中的值,調用Object.setPrototypeOf()方法改變其中的值。然而,這不是操作[[prototype]]值的唯一方法
ES6引入了super引用,使開發者可以更便捷的通路對象原型。
如果想重寫對象執行個體的方法,又需要調用與它同名的原型方法,利用super引用可以這樣寫
super引用相當于指向對象原型的指針,實際上也就是Object.getPrototypeOf(this)的值
如果用es5來寫這個示例,就要複雜一些,而且不容易了解
Super引用在多重繼承情況下非常有用,因為在這種情況下,使用Object.getPrototypeOf()方法将會出現問題
當執行p.sayName()方法時,會調用friend.sayName()方法,而此時的this值為p。Object.getPrototypeOf(this)又會傳回friend對象。是以就會進入遞歸調用直到觸發棧溢出報錯
如果使用super引用就不會有這種問題
super引用不是動态變化的,無論有多少其他方法繼承了sayName()方法,super.sayName()始終指向person.sayName()方法
在ES6以前從未正式定義過"方法"的概念,方法僅僅是一個具有功能而非資料的對象屬性。而在ES6中正式将方法定義為一個函數,它會有一個内部的[[HomeObject]]屬性來容納這個方法從屬的對象
當調用friend.sayName()方法時,該方法内部的[[HomeObject]]屬性值是friend,friend的原型是person,是以super.sayName()等價于person.sayName().call(this)
ES5 引入了<code>Object.keys()</code>方法,傳回一個數組,成員是參數對象自身的(不含繼承的)所有可周遊(enumerable)屬性的鍵名
ES8引入了Object.values和Object.entries,作為周遊一個對象的補充手段,供for...of循環使用
<code>Object.values()</code>方法傳回一個數組,成員是參數對象自身的(不含繼承的)所有可周遊(enumerable)屬性的鍵值
<code>Object.entries()</code>方法傳回一個數組,成員是參數對象自身的(不含繼承的)所有可周遊(enumerable)屬性的鍵值對數組
部落格: https://blog.86886.wang
GitHub: https://github.com/wmui