摘要:創(chuàng)建一個(gè)新對(duì)象將構(gòu)造函數(shù)的作用域賦給新對(duì)象因此就指向了這個(gè)新對(duì)象執(zhí)行構(gòu)造函數(shù)中的代碼為這個(gè)新對(duì)象添加屬性返回新對(duì)象。
本章內(nèi)容
理解對(duì)象屬性
理解并創(chuàng)建對(duì)象
理解繼承
ECMA-262把對(duì)象定義為:無序?qū)傩缘募?,其屬性可以包含基本值、?duì)象或者函數(shù)
理解對(duì)象創(chuàng)建自定義對(duì)象的最簡(jiǎn)單方式就是創(chuàng)建一個(gè)Object的實(shí)例,再為它添加屬性和方法。
var person = new Object(); person.name = "Nicholas"; person.age = 29; person.job = "Software Engineer"; person.sayName = function(){ alert(this.name); };
另一種方法,對(duì)象字面量成為創(chuàng)建對(duì)象的首選模式。
var person = { name: "Nicholas"; age: 29; job: "Software Engineer"; sayName: function(){ alert(this.name); } }
ECMA-262第五版在定義只有內(nèi)部才用的特性(attribute)時(shí),描述了屬性(property)的各種特性。特性用兩對(duì)方括號(hào)包含。
ECMAScript中有兩種屬性:數(shù)據(jù)屬性和訪問器屬性
1.數(shù)據(jù)屬性
要修改屬性默認(rèn)的特性,必須使用ECMAScript5的Object.defineProperty()方法。這個(gè)方法接收三個(gè)參數(shù):屬性所在的對(duì)象、屬性的名字和一個(gè)描述符對(duì)象。
var person = {}; Object.defineProperty(person, "name", { writable: false, value: "Nicholas" }); console.log(person.name);//Nicholas person.name = "Greg"; console.log(person.name);//Nicholas
2.訪問器屬性
var book = { _year: 2004, edition: 1 } Object.defineProperty(book, "year",{ get: function(){ return this._year; }, set: function(newValue){ if(newValue > 2004){ this._year = newValue; this.edition += newValue - 2004; } } }); book.year = 2005; console.log(book.edition);//2
_year前面的下下劃線是一種常用的記號(hào),用于表示只能通過對(duì)象方法訪問的屬性。
這是使用訪問器屬性的常見方法,即設(shè)置一個(gè)屬性的值會(huì)導(dǎo)致其他屬性發(fā)生變化。
只指定getter意味著屬性是不能寫
創(chuàng)建對(duì)象object構(gòu)造函數(shù)或者對(duì)象字面量都可以用來創(chuàng)建單個(gè)對(duì)象,但這些方式有個(gè)明顯的缺點(diǎn):使用同一個(gè)接口創(chuàng)建很多對(duì)象,會(huì)產(chǎn)生大量的重復(fù)代碼
用函數(shù)來封裝以特定接口創(chuàng)建對(duì)象的細(xì)節(jié)
function createPerson(name, age, job){ var o = new Object(); o.name = name; o.age = age; o.job = job; o.sayName = function(){ alert(this.name); } retrun o; } var person1 = createPerson("Nicholas", 29, "Software Engineer"); var person2 = createPerson("Greg", 27, "Doctor");
工廠模式雖然解決了創(chuàng)建多個(gè)相似對(duì)象的問題,但卻沒有解決對(duì)象識(shí)別的問題(怎樣知道一個(gè)對(duì)象的類型)
function Person(name,age,job){ this.name = name; this.job = job; this.age = age; this.sayName = function(){ alert(this.name); }; } var person1 = new Person("Trick",29,"SoftWare Engineer"); var person2 = new Person("John",23,"Doctor");
Person與createPerson函數(shù)存在以下不同之處:
沒有顯示地創(chuàng)建對(duì)象
直接將屬性和方法賦給了this對(duì)象
沒有return語句
要?jiǎng)?chuàng)建Person的新實(shí)例,必須使用new操作符。
創(chuàng)建一個(gè)新對(duì)象;
將構(gòu)造函數(shù)的作用域賦給新對(duì)象(因此this就指向了這個(gè)新對(duì)象);
執(zhí)行構(gòu)造函數(shù)中的代碼(為這個(gè)新對(duì)象添加屬性);
返回新對(duì)象。
person1和person2分別保存著Person的一個(gè)不同的實(shí)例。這兩個(gè)對(duì)象都有一個(gè)constructor(構(gòu)造函數(shù)),該屬性指向Person
alert(person1.constructor == Person);//true alert(person2.constructor == Person);//true
constructor最初是用來標(biāo)識(shí)對(duì)象類型的,檢測(cè)對(duì)象類型
instanceof操作符要更可靠一些,在以下例子中創(chuàng)建的所有對(duì)象既是Object的實(shí)例,同時(shí)也是Person的實(shí)例
alert(person1 instanceof Object);//true alert(person1 instanceof Person);//true alert(person2 instanceof Object);//true alert(person2 instanceof Person);//true
將構(gòu)造函數(shù)當(dāng)作函數(shù)
構(gòu)造函數(shù)與其他函數(shù)的唯一區(qū)別,就在于調(diào)用它們的方式不同。任何函數(shù),只要通過new操作符,那它就可以作為構(gòu)造函數(shù);而任何函數(shù),如果不通過new操作符來調(diào)用,那它跟普通函數(shù)也不會(huì)有什么兩樣
//當(dāng)作構(gòu)造函數(shù)使用 var person = new Person("Nicholas", 29, "Software Engineer"); person.sayName(); //作為普通函數(shù)調(diào)用 Person("Greg", 27, "Doctor");//添加到window window.sayName();//"Greg" //在另外一個(gè)對(duì)象的作用域中調(diào)用 var o = new Object(); Person.call(o, "Kristen", 25, "Nurse"); o.sayName();
每個(gè)方法都要在每個(gè)實(shí)例上創(chuàng)建一遍,前面的例子中,person1和person2都有一個(gè)名為sayName()的方法,但那兩個(gè)方法不是Function的實(shí)例。在ECMAScript中的函數(shù)是對(duì)象,因此每定義一個(gè)函數(shù),也就是實(shí)例化了一個(gè)對(duì)象
function Person(name, age, job){ this.name = name; this.age = age; this.job = job; this.sayName = new Function("alert(this.name)"); //與聲明函數(shù)在邏輯上是等價(jià)的 }
通過把函數(shù)定義轉(zhuǎn)移到構(gòu)造函數(shù)外部來解決這個(gè)問題。
function Person(name, age, job){ this.name = name; this.age = age; this.job = job; this.sayName = sayName; } function sayName(){ alert(this.name); } var person1 = new Person("Nicholas", 29, "Software Engineer"); var person2 = new Person("Greg", 27, "Doctor");
這么做問題又來了,全局作用域中定義的函數(shù)實(shí)際上只能被某個(gè)對(duì)象調(diào)用,這讓全局作用域名不副實(shí);并且如果有多個(gè)對(duì)象,對(duì)象又各自有多個(gè)方法,那就要定義很多個(gè)全局函數(shù),就沒有封裝性可言了
待續(xù)....
文章版權(quán)歸作者所有,未經(jīng)允許請(qǐng)勿轉(zhuǎn)載,若此文章存在違規(guī)行為,您可以聯(lián)系管理員刪除。
轉(zhuǎn)載請(qǐng)注明本文地址:http://systransis.cn/yun/98502.html
摘要:高程讀書筆記第六章理解對(duì)象創(chuàng)建自定義對(duì)象的方式有創(chuàng)建一個(gè)實(shí)例,然后為它添加屬性和方法。創(chuàng)建了自定義的構(gòu)造函數(shù)之后,其原型對(duì)象默認(rèn)只會(huì)取得屬性至于其他方法都是從繼承而來的。 JS高程讀書筆記--第六章 理解對(duì)象 創(chuàng)建自定義對(duì)象的方式有創(chuàng)建一個(gè)Object實(shí)例,然后為它添加屬性和方法。還可用創(chuàng)建對(duì)象字面量的方式 屬性類型 ECMAScript在定義只有內(nèi)部采用的特性時(shí),描述了屬性的各種特征...
摘要:三種使用構(gòu)造函數(shù)創(chuàng)建對(duì)象的方法和的作用都是在某個(gè)特殊對(duì)象的作用域中調(diào)用函數(shù)。這種方式還支持向構(gòu)造函數(shù)傳遞參數(shù)。叫法上把函數(shù)叫做構(gòu)造函數(shù),其他無區(qū)別適用情境可以在特殊的情況下用來為對(duì)象創(chuàng)建構(gòu)造函數(shù)。 一、工廠模式 工廠模式:使用字面量和object構(gòu)造函數(shù)會(huì)有很多重復(fù)代碼,在此基礎(chǔ)上改進(jìn)showImg(https://segmentfault.com/img/bVbmKxb?w=456&...
摘要:在復(fù)雜的情況下,需要具體策略維護(hù)內(nèi)部狀態(tài)時(shí),可能需要把策略和享元模式結(jié)合起來。函數(shù)比用戶定義的類的實(shí)例輕量,而且無需使用享元模式,因?yàn)楦鱾€(gè)策略函數(shù)在編譯模塊時(shí)只會(huì)創(chuàng)建一次。 一等函數(shù)實(shí)現(xiàn)設(shè)計(jì)模式 經(jīng)典的策略模式定義 定義一系列算法,把它們一一封裝起來,并且使它們可以相互替換。本模式使得算法可以獨(dú)立于使用它的客戶而變化。 案例 假如一個(gè)網(wǎng)店制定了下述折扣規(guī)則。 有 1000 或以上積分...
摘要:繼承的是超類型中構(gòu)造函數(shù)中的屬性,如上繼承了屬性,但沒有繼承原型中的方法。上述造成的結(jié)果是子類型實(shí)例中有兩組超類型的構(gòu)造函數(shù)中定義的屬性,一組在子類型的實(shí)例中,一組在子類型實(shí)例的原型中。 ECMAScript只支持實(shí)現(xiàn)繼承,主要依靠原型鏈來實(shí)現(xiàn)。與實(shí)現(xiàn)繼承對(duì)應(yīng)的是接口繼承,由于script中函數(shù)沒有簽名,所以無法實(shí)現(xiàn)接口繼承。 一、原型鏈 基本思想:利用原型讓一個(gè)引用類型繼承另一個(gè)引用...
摘要:分區(qū)函數(shù)返回一個(gè)布爾值,這意味著得到的分組的鍵類型是,于是它最多可以分為兩組是一組,是一組。當(dāng)遍歷到流中第個(gè)元素時(shí),這個(gè)函數(shù)執(zhí)行時(shí)會(huì)有兩個(gè)參數(shù)保存歸約結(jié)果的累加器已收集了流中的前個(gè)項(xiàng)目,還有第個(gè)元素本身。 一、收集器簡(jiǎn)介 把列表中的交易按貨幣分組: Map transactionsByCurrencies = transactions.stream().collect(groupi...
閱讀 1715·2023-04-26 01:02
閱讀 4879·2021-11-24 09:39
閱讀 1815·2019-08-30 15:44
閱讀 2900·2019-08-30 11:10
閱讀 1795·2019-08-30 10:49
閱讀 993·2019-08-29 17:06
閱讀 619·2019-08-29 16:15
閱讀 910·2019-08-29 15:17