JavaScript創(chuàng)建對象幾種形式

方式一: Object構(gòu)造函數(shù)模式

  • 套路: 先創(chuàng)建空Object對象, 再動態(tài)添加屬性/方法
  • 適用場景: 起始時不確定對象內(nèi)部數(shù)據(jù)
  • 問題: 語句太多
 var p = new Object()//先創(chuàng)建空Object對象
 p.name = 'Tom'
 p.age = 12
 p.setName = function (name) {
   this.name = name
 }

方式二: 對象字面量模式

  • 套路: 使用{}創(chuàng)建對象, 同時指定屬性/方法
  • 適用場景: 起始時對象內(nèi)部數(shù)據(jù)是確定的
  • 問題: 如果創(chuàng)建多個對象, 有重復(fù)代碼
  var p = {
  name: 'Tom',
  age: 12,
  setName: function (name) {
    this.name = name
  }
}

方式三: 工廠模式

  • 套路: 通過工廠函數(shù)動態(tài)創(chuàng)建對象并返回
  • 適用場景: 需要創(chuàng)建多個對象
  • 問題: 對象沒有一個具體的類型, 都是Object類型
 function createPerson(name, age) { 
  var obj = {//返回一個對象的函數(shù)
    name: name,
    age: age,
    setName: function (name) {
      this.name = name
    }
  }
  return obj
}

工廠模式無法識別對象的類型,因為它們直接由 Object() 構(gòu)造函數(shù)創(chuàng)建一忱,原型鏈上只有 Object.prototype 對象魁亦,不像Date叠赐、Array等泳赋。

方式四: 自定義構(gòu)造函數(shù)模式

  • 套路: 自定義構(gòu)造函數(shù), 通過new創(chuàng)建對象
  • 適用場景: 需要創(chuàng)建多個類型確定的對象
  • 問題: 每個對象都有相同的數(shù)據(jù), 浪費內(nèi)存

構(gòu)造函數(shù)的目的就是為了創(chuàng)建一個自定義類爸舒,并且創(chuàng)建這個類的實例臣淤。構(gòu)造函數(shù)模式中擁有了類和實例的概念顶猜,并且實例和實例之間是相互獨立的,即實例識別粤剧。

構(gòu)造函數(shù)就是一個普通的函數(shù)歇竟,創(chuàng)建方式和普通函數(shù)沒有區(qū)別,不同的是構(gòu)造函數(shù)習(xí)慣上首字母大寫抵恋。另外就是調(diào)用方式的不同焕议,普通函數(shù)是直接調(diào)用,而構(gòu)造函數(shù)需要使用new關(guān)鍵字來調(diào)用弧关。

1.構(gòu)造函數(shù)的執(zhí)行流程:

1.立刻創(chuàng)建一個新的對象

2.將新建的對象設(shè)置為函數(shù)中this

3.逐行執(zhí)行函數(shù)中的代碼

4.將新建的對象作為返回值返回

function Person(name, age) {
   this.name = name
   this.age = age
   this.setName = function (name) {
     this.name = name
   }
 }
var p1 = new Person('Tom', 12)
function Student(name, price) {
     this.name = name
     this.price = price
     this.setName = function (name) {
       this.name = name
     }
   }
 var s1 = new Student('Bob', 13000)
 console.log(p1 instanceof Person)//true
 console.log(s1 instanceof Student)//true
 console.log(p1,s1)

image

使用instanceof可以檢查一個對象是否是一個類的實例盅安。所有的對象都是Object的后代,所以任何對象和Object左instanceof檢查時都會返回true世囊。

2.注意點

p1和p2都是Person這個類的實例别瞭,所以都擁有setName這個方法,但是不同實例之間的方法是不一樣的株憾。在類中給實例增加的屬性(this.xxx=xxx)屬于當(dāng)前實例的私有的屬性蝙寨,實例和實例之間是單獨的個體晒衩,所以私有的屬性之間是不相等的。

var p2 = new Person('jack', 12)
console.log(p1.setName === p2.setName);

每創(chuàng)建一個Person構(gòu)造函數(shù)墙歪,在Person構(gòu)造函數(shù)中听系,為每一個對象都添加了一個setName方法,也就是說構(gòu)造函數(shù)每執(zhí)行一次就會創(chuàng)建一個新的setName方法箱亿。這樣就導(dǎo)致了構(gòu)造函數(shù)執(zhí)行一次就會創(chuàng)建一個新的方法跛锌,執(zhí)行10000次就會創(chuàng)建10000個新的方法,而10000個方法都是一模一樣的届惋,這是完全沒有必要髓帽,完全可以使所有的對象共享同一個方法。

function Person(name, age) {
   this.name = name
   this.age = age
   this.setName = fun
 }
function fun(){
   alert("Hello大家好脑豹,我是:"+this.name);
};

將函數(shù)定義在全局作用域這種方法郑藏,雖然會提升性能,但污染了全局作用域的命名空間,而且定義在全局作用域中也很不安全瘩欺。那么有沒有更好的辦法呢必盖?

方式五: 構(gòu)造函數(shù)+原型的組合模式

  • 套路: 自定義構(gòu)造函數(shù), 屬性在函數(shù)中初始化, 方法添加到原型上
  • 適用場景: 需要創(chuàng)建多個類型確定的對象

我們所創(chuàng)建的每一個函數(shù),解析器都會向函數(shù)中添加一個屬性prototype俱饿,這個屬性對應(yīng)著一個對象歌粥,這個對象就是我們所謂的原型對象。如果函數(shù)作為普通函數(shù)調(diào)用prototype沒有任何作用拍埠。當(dāng)函數(shù)以構(gòu)造函數(shù)的形式調(diào)用時失驶,它所創(chuàng)建的對象中都會有一個隱含的屬性,指向該構(gòu)造函數(shù)的原型對象枣购,我們可以通過__proto__來訪問該屬性嬉探。

    function MyClass() {}
    var mc = new MyClass()
    console.log(mc.__proto__ === MyClass.prototype)//true

原型對象就相當(dāng)于一個公共的區(qū)域,所有同一個類的實例都可以訪問到這個原型對象棉圈,我們可以將對象中共有的內(nèi)容涩堤,統(tǒng)一設(shè)置到原型對象中。當(dāng)我們訪問對象的一個屬性或方法時分瘾,它會先在對象自身中尋找胎围,如果有則直接使用,如果沒有則會去原型對象中尋找德召,如果找到則直接使用白魂。如果沒有則去原型的原型中尋找,直到找到Object對象的原型,Object對象的原型沒有原型氏捞,如果在Object原型中依然沒有找到,則返回undefined冒版。

 function Person(name, age) { //在構(gòu)造函數(shù)中只初始化一般函數(shù)
   this.name = name
   this.age = age
 }
 Person.prototype.setName = function (name) {
   this.name = name
 }
 var p1 = new Person('Tom', 23)
 var p2 = new Person('Jack', 24)
 console.log(p1, p2)
image
  p1.setName("james")//p1沒有這個方法液茎,就會去原型對象中尋找
  console.log(p1)//Person{name: "james", age: 23}

以后我們創(chuàng)建構(gòu)造函數(shù)時,可以將這些對象共有的屬性和方法,統(tǒng)一添加到構(gòu)造函數(shù)的原型對象中捆等,這樣不用分別為每一個對象添加滞造,也不會影響到全局作用域,就可以使每個對象都具有這些屬性和方法了栋烤。

如果覺得文章對你有些許幫助谒养,歡迎在我的GitHub博客點贊和關(guān)注,感激不盡明郭!

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
  • 序言:七十年代末买窟,一起剝皮案震驚了整個濱河市,隨后出現(xiàn)的幾起案子薯定,更是在濱河造成了極大的恐慌始绍,老刑警劉巖,帶你破解...
    沈念sama閱讀 221,635評論 6 515
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件话侄,死亡現(xiàn)場離奇詭異亏推,居然都是意外死亡,警方通過查閱死者的電腦和手機(jī)年堆,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 94,543評論 3 399
  • 文/潘曉璐 我一進(jìn)店門吞杭,熙熙樓的掌柜王于貴愁眉苦臉地迎上來,“玉大人变丧,你說我怎么就攤上這事芽狗。” “怎么了锄贷?”我有些...
    開封第一講書人閱讀 168,083評論 0 360
  • 文/不壞的土叔 我叫張陵译蒂,是天一觀的道長。 經(jīng)常有香客問我谊却,道長柔昼,這世上最難降的妖魔是什么? 我笑而不...
    開封第一講書人閱讀 59,640評論 1 296
  • 正文 為了忘掉前任炎辨,我火速辦了婚禮捕透,結(jié)果婚禮上,老公的妹妹穿的比我還像新娘碴萧。我一直安慰自己乙嘀,他們只是感情好,可當(dāng)我...
    茶點故事閱讀 68,640評論 6 397
  • 文/花漫 我一把揭開白布破喻。 她就那樣靜靜地躺著虎谢,像睡著了一般。 火紅的嫁衣襯著肌膚如雪曹质。 梳的紋絲不亂的頭發(fā)上婴噩,一...
    開封第一講書人閱讀 52,262評論 1 308
  • 那天擎场,我揣著相機(jī)與錄音,去河邊找鬼几莽。 笑死迅办,一個胖子當(dāng)著我的面吹牛,可吹牛的內(nèi)容都是我干的章蚣。 我是一名探鬼主播站欺,決...
    沈念sama閱讀 40,833評論 3 421
  • 文/蒼蘭香墨 我猛地睜開眼,長吁一口氣:“原來是場噩夢啊……” “哼纤垂!你這毒婦竟也來了矾策?” 一聲冷哼從身側(cè)響起,我...
    開封第一講書人閱讀 39,736評論 0 276
  • 序言:老撾萬榮一對情侶失蹤洒忧,失蹤者是張志新(化名)和其女友劉穎蝴韭,沒想到半個月后,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體熙侍,經(jīng)...
    沈念sama閱讀 46,280評論 1 319
  • 正文 獨居荒郊野嶺守林人離奇死亡榄鉴,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點故事閱讀 38,369評論 3 340
  • 正文 我和宋清朗相戀三年,在試婚紗的時候發(fā)現(xiàn)自己被綠了蛉抓。 大學(xué)時的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片庆尘。...
    茶點故事閱讀 40,503評論 1 352
  • 序言:一個原本活蹦亂跳的男人離奇死亡,死狀恐怖巷送,靈堂內(nèi)的尸體忽然破棺而出驶忌,到底是詐尸還是另有隱情,我是刑警寧澤笑跛,帶...
    沈念sama閱讀 36,185評論 5 350
  • 正文 年R本政府宣布付魔,位于F島的核電站,受9級特大地震影響飞蹂,放射性物質(zhì)發(fā)生泄漏几苍。R本人自食惡果不足惜,卻給世界環(huán)境...
    茶點故事閱讀 41,870評論 3 333
  • 文/蒙蒙 一陈哑、第九天 我趴在偏房一處隱蔽的房頂上張望妻坝。 院中可真熱鬧,春花似錦惊窖、人聲如沸刽宪。這莊子的主人今日做“春日...
    開封第一講書人閱讀 32,340評論 0 24
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽圣拄。三九已至,卻和暖如春毁欣,著一層夾襖步出監(jiān)牢的瞬間庇谆,已是汗流浹背赁遗。 一陣腳步聲響...
    開封第一講書人閱讀 33,460評論 1 272
  • 我被黑心中介騙來泰國打工, 沒想到剛下飛機(jī)就差點兒被人妖公主榨干…… 1. 我叫王不留族铆,地道東北人。 一個月前我還...
    沈念sama閱讀 48,909評論 3 376
  • 正文 我出身青樓哭尝,卻偏偏與公主長得像哥攘,于是被迫代替她去往敵國和親。 傳聞我的和親對象是個殘疾皇子材鹦,可洞房花燭夜當(dāng)晚...
    茶點故事閱讀 45,512評論 2 359

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

  • ??面向?qū)ο螅∣bject-Oriented桶唐,OO)的語言有一個標(biāo)志栅葡,那就是它們都有類的概念,而通過類可以創(chuàng)建任意...
    霜天曉閱讀 2,112評論 0 6
  • 面向?qū)ο螅∣bject-Oriented,OO)的語言有一個標(biāo)志尤泽,那就是它們都有類的慨念欣簇,而通過類可以創(chuàng)建任意多個...
    threetowns閱讀 878評論 0 4
  • 第3章 基本概念 3.1 語法 3.2 關(guān)鍵字和保留字 3.3 變量 3.4 數(shù)據(jù)類型 5種簡單數(shù)據(jù)類型:Unde...
    RickCole閱讀 5,130評論 0 21
  • 《活出生命的意義》——弗蘭克爾 第五六章一些讓人有感觸的話 1.我總能經(jīng)受住生活中的各種傷害和責(zé)難,這大概要歸功于...
    Pheeb閱讀 194評論 0 0
  • 我們常說的青筋就是靜脈小血管∧重ぃ總的來說横殴,手上青筋出現(xiàn)的越少越健康。 根據(jù)青筋的位置卿拴、長短和深淺衫仑,就可以知道是身體哪...
    雨露yangzhengju閱讀 2,378評論 0 0