JS對(duì)象

本節(jié)主要介紹對(duì)象的屬性類型以及創(chuàng)建對(duì)象的幾種方法。

對(duì)象的屬性類型:

ES中只有兩種屬性:數(shù)據(jù)屬性和訪問器屬性。

數(shù)據(jù)屬性

[[Configurable]]: 是否可配置,如能否delete刪除屬性,能否修改為訪問器屬性等。
[[Enumerable]]: 能否通過for-in返回屬性。內(nèi)置對(duì)象自帶的原型屬性是不可枚舉的。
[[Writable]]: 能否修改屬性值。
[[Value]]: 屬性的數(shù)據(jù)值。

訪問器屬性

[[Configurable]]:能否修改屬性特征,能否delete刪除屬性,能否修改為訪問器屬性。
[[Enumerable]]: 能否通過for-in返回屬性。
[[Set]]: 寫入屬性時(shí)調(diào)用。
[[Get]]: 讀取屬性時(shí)調(diào)用。

訪問器屬性必須使用Object.defineProperty()定義。

var person = {
  name: 'John',
  surname: 'Smith',
}
Object.defineProperty(person, "fullname",{
  get: function(){
    return this.name + ' ' + this.surname
  },
  set: function(value){
    this.name = value.split(' ')[0]
    this.surname = value.split(' ')[1]
  }
})
console.log(person.fullname)//'John Smith'
person.surname = 'Brown'
console.log(person.fullname)//'John Brown'
person.fullname = 'Ami Smith'
console.log(person.name)//'Ami'

創(chuàng)建對(duì)象的幾種方法對(duì)比:

1.對(duì)象字面量
var person1 = {
  name: '小強(qiáng)',
  age: 29,
  sayName: function () {
    console.log(this.name)
  }
}
var person2 = {
  name: '小紅',
  age: 10,
  sayName: function () {
    console.log(this.name)
  }
}

上面通過對(duì)象字面量的方式創(chuàng)建了兩個(gè)對(duì)象,person1和person2。這種方法創(chuàng)建對(duì)象會(huì)產(chǎn)生大量的重復(fù)代碼。

2.工廠模式
function createPerson (name, age) {
  var o = new Object()
  o.name = name
  o.age = age
  o.sayName = function () {
    console.log(this.name)
  }
  return o
}
var person1 = createPerson('小強(qiáng)', 10)
var person2 = createPerson('小紅', 10)
image.png

工廠模式?jīng)]有創(chuàng)建特定的對(duì)象類型,無法進(jìn)行對(duì)象的識(shí)別。

3.構(gòu)造函數(shù)模式
function Person (name, age) {
  this.name = name
  this.age = age
  this.sayName = function () {
    console.log(this.name)
  }
}
var person1 = new Person('小強(qiáng)', 10)
var person2 = new Person('小紅', 10)
image.png
  • 構(gòu)造函數(shù)的方法與上述工廠模式相比,有以下區(qū)別:

1.沒有顯示的創(chuàng)建對(duì)象;
2.函數(shù)內(nèi)部使用this,將屬性和方法都寫到this上。
3.沒有return返回值

  • 構(gòu)造函數(shù)的方法有個(gè)new Person()的過程,new的時(shí)候發(fā)生了什么?

1.創(chuàng)建一個(gè)新的對(duì)象;
2.把構(gòu)造函數(shù)的作用域賦給這個(gè)新對(duì)象,這樣this就指向了這個(gè)對(duì)象;
3.執(zhí)行構(gòu)造函數(shù)的代碼,將屬性和方法添加到新對(duì)象上;
4.返回這個(gè)新對(duì)象。

  • 如何判斷對(duì)象類型?
    通過constructor屬性判斷,該屬性指向構(gòu)造函數(shù)。


    image.png
  • 構(gòu)造函數(shù)的缺點(diǎn):
    構(gòu)造函數(shù)上的方法在每個(gè)實(shí)例上都是不同的方法,都需要重新創(chuàng)建一遍。

console.log(person1.sayName===person2.sayName)  //false
4. 原型模式

每個(gè)函數(shù)都有一個(gè)原型屬性(prototype),這個(gè)屬性是一個(gè)指針,指向一個(gè)對(duì)象,該對(duì)象包含所有實(shí)例對(duì)象可以共享的屬性和方法。

function Person(name, age){
  this.name = name
  this.age = age
}
Person.prototype.sayName = function(){
  console.log(this.name)
}
Person.prototype.smart = true
var person1 = new Person('小強(qiáng)',10)
var person2 = new Person('小紅',10)
image.png
image.png
  • 如何判斷對(duì)象的屬性是在原型對(duì)象上還是實(shí)例對(duì)象上定義的?
    利用in可以判斷是否可以訪問到該屬性;
    利用hasOwnProperty可以判斷實(shí)例中是否存在該屬性;
    兩者結(jié)合可以判斷該屬性是否只存在于原型中。
var person1 = new Person('小強(qiáng)',10)
var person2 = new Person('小紅',10)
person1.smart=false
//是否能訪問到該屬性
console.log("smart" in person1)//true
console.log("smart" in person2)//true
//實(shí)例中是否存在該屬性
console.log(person1.hasOwnProperty("smart"))//true
console.log(person2.hasOwnProperty("smart"))//false
//屬性是否只存在于原型中
console.log(("smart" in person1)&& !(person1.hasOwnProperty("smart")))//false
console.log(("smart" in person1) && !(person2.hasOwnProperty("smart")))//true
  • 原型的利用:添加一個(gè)所有實(shí)例可訪問的共享屬性。
var time=new Date()
Date.prototype.format=function(){
  return (this.getMonth() + 1) + '-'+this.getDate()
}
var formatTime = time.format()

創(chuàng)建對(duì)象的總結(jié)

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

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

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