成人国产在线小视频_日韩寡妇人妻调教在线播放_色成人www永久在线观看_2018国产精品久久_亚洲欧美高清在线30p_亚洲少妇综合一区_黄色在线播放国产_亚洲另类技巧小说校园_国产主播xx日韩_a级毛片在线免费

資訊專欄INFORMATION COLUMN

JS面向?qū)ο蠖?this/原型鏈/new原理

anRui / 1281人閱讀

摘要:情況沒有明確作用對象的情況下,通常為全局對象例如函數(shù)的回調(diào)函數(shù),它的就是全局對象。正因如此,機器可以作為這類對象的標(biāo)志,即面向?qū)ο笳Z言中類的概念。所以機器又被稱為構(gòu)造函數(shù)。原型鏈也就是繼承鏈。

JS面向?qū)ο蠖?this/原型鏈/new原理

阮一峰JavaScript教程:面向?qū)ο缶幊?/p>

阮一峰JavaScript教程:實例對象與 new 命令

阮一峰JavaScript教程:this 關(guān)鍵字

也可以看看這篇文章周大俠啊 進擊的 JavaScript(六) 之 this先了解一下`this的四種綁定規(guī)則和箭頭函數(shù)的this綁定

this

這兩篇文章寫的很好
周大俠啊 進擊的 JavaScript(六) 之 this

蘇云的博客

下面的this分別是什么?這幾個函數(shù)都是回調(diào)函數(shù),回調(diào)函數(shù)this比較特殊,通常是事件原對象

//1.
button1.onclick = function () {
    console.log(this)
}
//2.
button2.addEventListener("click", function () {
    console.log(this)
})
//3.jQuery中
$("ul").on("click", "li", function () {
    console.log(this)
})

this是函數(shù).call()的第一個參數(shù).

那么在直接調(diào)用函數(shù)的時候(隱式綁定,沒用call),如何知道call()的第一個參數(shù)?
源碼看不到,那就看文檔.

看文檔!:
onclick:

addEventListener:

jQuery中:

所以上面三個的this分別是
btutton1元素,button2元素,li元素

$("ul").on("click", "li"/*selector*/, function () {
console.log(this)//代表與selector相匹配的元素(li元素)
})

thiscall()的第一個參數(shù),只有寫onclick,寫addEventListener和寫jQueryon的人想call()哪個東西,就把這個this綁定到哪里去了,所以要確定this,就要看源碼或者文檔!

例如:

button1.onclick = function () {
    console.log(this)
}
button1.onclick.call({name:"mataotao"})

可以直接觸發(fā)onclick事件,傳入{name:"mataotao"},那么this就是{name:"mataotao"}這個對象

以下來自蘇云的博客()

6.回調(diào)函數(shù)的this 回調(diào)函數(shù)也只不過是函數(shù)的一種,實際上這種情況已經(jīng)包含在了前面提到的情況中。但是由于回調(diào)函數(shù)的調(diào)用者往往不是我們自己,而是回調(diào)函數(shù)的接收者,即某個庫或框架、甚至是JS運行時環(huán)境。這樣一來,回調(diào)函數(shù)在中的this是什么就與對方的調(diào)用方式有關(guān)了,因此變得比較復(fù)雜,所以多帶帶拿出來討論一下。

情況1:沒有明確作用對象的情況下,通常this為全局對象

例如setTimeout函數(shù)的回調(diào)函數(shù),它的this就是全局對象。你如果希望自己指定this,可以通過bind函數(shù)等方法。

情況2:某個事件的監(jiān)聽器回調(diào)函數(shù),通常this就是事件源對象

例如:

button.addEventListener("click", fn)

fn的中的this就是事件源button對象。

情況3:某些API會專門提供一個參數(shù),用來指定回調(diào)函數(shù)中的this

例如,我們可以重新設(shè)計一個可以指定thissetTimeout

function setTimeoutExt(cb, period, thisArg) {
    setTimeout(function() {
        cb.call(thisArg);
    }, period); }

另外,在ExtJS中也大量使用了可以指定this的接口。

this題目

答案:
調(diào)用B處的console.log().結(jié)果是options
window(console.log()中console是全局window對象里的一個方法)

第二題:

答案:D Object

第三題:

答案:Object

原型鏈

我終于明白了原型鏈:
仔細看下面這篇文章,就能明白原型鏈的構(gòu)造問題:
JavaScript 世界萬物誕生記

個人理解:
原型鏈要分為兩個部分,原型和鏈,原型就是一個實例對象,但是是最基礎(chǔ)的實例對象.這個實例對象可以作為模板/類,讓其他對象去復(fù)制他,復(fù)制之后不單單有這個原型的屬性,也可以有自己的屬性.新實現(xiàn)的實例對象.__proto__指向原來的模板實例對象.
而造出來的對象也可以當(dāng)做模板,再由新的機器去以他為模板造新對象.由此形成了一條__proto__組成的鏈.
所有的對象都有__proto__屬性,他們就像被鏈子連接在了一起,所以就稱之為原型鏈

而復(fù)制的過程由一個機器來完成.這個機器(比如可以說是Object())的使用方法就是:按照模板實例對象new()一個新對象,新對象被原來的模板對象用__proto__鏈子拴著,新對象可以有自己的新添加的東西.
這個按照模板造新對象的機器.prototype指向原來的模板實例對象.prototype就是原來的模板實例對象拴住復(fù)制自己機器的鏈子.

寫成代碼就是:

var obj = new Object({ flag: 10 });
就像前面所說,機器用來制造某一類對象。正因如此,機器可以作為這類對象的標(biāo)志,即面向?qū)ο笳Z言中(class)的概念。所以機器又被稱為構(gòu)造函數(shù)。在ES6引入class關(guān)鍵字之前,我們常常把構(gòu)造函數(shù)叫做類。

說明2:用戶自定義的函數(shù)通常既可以作為普通函數(shù)使用,又可以作為構(gòu)造函數(shù)來制造對象。ES6新增的class語法定義的函數(shù)只能作為構(gòu)造函數(shù),ES6新增的=>語法定義的箭頭函數(shù)只能作為普通函數(shù)。

.

__proto__prototype的區(qū)別
__proto__是所有對象(包括函數(shù)對象)都有的一個屬性(當(dāng)然只是邏輯上有這么個概念),當(dāng)我們說“原型鏈”的時候,就是指對象通過這個屬性互相連接而形成的鏈狀結(jié)構(gòu)。原型鏈也就是繼承鏈。
prototype是只有函數(shù)(準(zhǔn)確地說是構(gòu)造函數(shù))才有的一個屬性,例如對于對于某個函數(shù)Fun。它的意義在于,當(dāng)你用var obj = new
Fun() 得到一個對象obj時,這個obj的原型就是F.prototype。即(new Fun()).__proto__ ===Fun.prototype,見文中第4個圖。

No. 1其實就是Object.prototype,No.
2其實就是Function.prototype。我只是為了強調(diào)這兩個對象的重要性,故意這樣說的。不太嚴(yán)格地說,前者就是一個空對象類似:{}
,后者就是一個空函數(shù),類似:fubction() {} 。

文中:
**No. 1:Object.prototype
No. 2:Function.prototype**

還有這幾篇文章也不錯:
「每日一題」什么是 JS 原型鏈? - 方應(yīng)杭的文章 - 知

周大俠啊 進擊的 JavaScript 之 (七) 原型鏈

周大俠啊 進擊的 JavaScript (八) 之 繼承

new()

看看這篇文章很清楚:
JS 的 new 到底是干什么的? - 方應(yīng)杭的文章 - 知乎

new解決了什么

以共有屬性對象為模板new出來的新對象的__proto__指向共有屬性對象(我把這個對象叫做模板對象,也叫作原型).這樣共有屬性在內(nèi)存中只需要存一次!

比如:當(dāng)我們造士兵的時候,士兵有共有屬性,有自有屬性,那么我們可以把共有屬性放在一個地方,避免每一次創(chuàng)建士兵都把共有屬性重新創(chuàng)建一次,浪費內(nèi)存:

既然這樣,那么我們可以把制造士兵的過程寫成一個函數(shù).

然后調(diào)用即可

直接使用函數(shù)就可以制造一個有特殊的id,但是__proto__指向原型士兵的新士兵

那么可不可以直接把這個原型對象放到函數(shù)里,組成一個整體?不行,這樣每次調(diào)用這個函數(shù),都會在內(nèi)存中創(chuàng)建這個臨時對象,那么和原先的不用原型一樣了

解決方法是,把這個原型變?yōu)楹瘮?shù)的一個屬性

這種方法省內(nèi)存且好用.

new()就是剛剛的所有過程

灰色的代碼就是new()做的封裝,不需要你做的事情
共有屬性被new()統(tǒng)一叫做prototype

new其實就是語法糖!

注意:.prototype對象最開始就是一個擁有constructor屬性的對象,如果想修改共有屬性,兩種方法:

當(dāng)我們new的時候我們做了什么:

new()的核心就是:

new應(yīng)用舉例:

第一步寫私有屬性,第二步寫共有屬性.

可以看到這個對象的
1自有屬性,
2__proto__指向的原型對象含有共有屬性.
3constructor指向的構(gòu)造函數(shù)

節(jié)選文章

也可以看看這篇文章周大俠啊 進擊的 JavaScript(六) 之 this
里面有new的實現(xiàn).new與this
下面是節(jié)選:

五、new 綁定 如果 使用 new 來創(chuàng)建對象,因為
后面跟著的是構(gòu)造函數(shù),所以稱它為構(gòu)造器調(diào)用。對于this綁定來說,稱為new綁定。

想知道 構(gòu)造器調(diào)用 中 this 的綁定,就要知道 new 到底做了啥了。

先來個 new 的實現(xiàn)??床欢灰o,在后面原型鏈那篇,還會說的。

function New(proto){  //proto 為傳進來的構(gòu)造函數(shù)
    var obj = {};
    obj.__proto__ = proto.prototype;

    proto.apply(obj, Array.prototype.slice.call(argument,1));
    //你這要看懂這步就行。這里把構(gòu)造函數(shù)里的 this  綁定到了 新的obj 對象上,最后 返回了該新對象,作為實例對象。

    return obj; }

所以在使用 new 來創(chuàng)建實例對象時,new 內(nèi)部把 構(gòu)造函數(shù)的 this 綁定到 返回的新對象 上了。

function Person(name){
    this.name = name; } var c = new Person("zdx"); c.name;

JavaScript 世界萬物誕生記中也提到了new的使用,new的過程就是生產(chǎn)機器按照模板原型對象造出來的新對象的過程!

文章版權(quán)歸作者所有,未經(jīng)允許請勿轉(zhuǎn)載,若此文章存在違規(guī)行為,您可以聯(lián)系管理員刪除。

轉(zhuǎn)載請注明本文地址:http://systransis.cn/yun/108408.html

相關(guān)文章

  • 前端進擊的巨人(七):走進面向對象,原型原型,繼承方式

    摘要:除了以上介紹的幾種對象創(chuàng)建方式,此外還有寄生構(gòu)造函數(shù)模式穩(wěn)妥構(gòu)造函數(shù)模式。 showImg(https://segmentfault.com/img/remote/1460000018196128); 面向?qū)ο?是以 對象 為中心的編程思想,它的思維方式是構(gòu)造。 面向?qū)ο?編程的三大特點:封裝、繼承、多態(tài): 封裝:屬性方法的抽象 繼承:一個類繼承(復(fù)制)另一個類的屬性/方法 多態(tài):方...

    wums 評論0 收藏0
  • 面向對象的 JavaScript

    摘要:是完全的面向?qū)ο笳Z言,它們通過類的形式組織函數(shù)和變量,使之不能脫離對象存在。而在基于原型的面向?qū)ο蠓绞街?,對象則是依靠構(gòu)造器利用原型構(gòu)造出來的。 JavaScript 函數(shù)式腳本語言特性以及其看似隨意的編寫風(fēng)格,導(dǎo)致長期以來人們對這一門語言的誤解,即認為 JavaScript 不是一門面向?qū)ο蟮恼Z言,或者只是部分具備一些面向?qū)ο蟮奶卣?。本文將回歸面向?qū)ο蟊疽猓瑥膶φZ言感悟的角度闡述為什...

    novo 評論0 收藏0
  • 我來重新學(xué)習(xí)js面向對象(part 4)

    摘要:我是的可以改變函數(shù)的對象的指向拋出異常,沒有這個因為子類和超類都是構(gòu)造函數(shù),那么就會有之前說的,構(gòu)造函數(shù)在的時候,里面的方法函數(shù)會重復(fù)創(chuàng)建實例,導(dǎo)致資源浪費。 我來重新學(xué)習(xí)js 的面向?qū)ο螅╬art 4) 續(xù)上一篇,隨著業(yè)務(wù)越來越大,要考慮一些繼承的玩意了,大千世界,各種東西我們要認識和甄別是需要靠大智慧去分門別類,生物學(xué)中把動植物按界、門、綱、目、科、屬、種進行分類的方法可能是最有代...

    MAX_zuo 評論0 收藏0
  • js面向對象淺談(三)

    摘要:還有一個問題,就是不能在創(chuàng)建子類性時,像父類型的構(gòu)造函數(shù)傳遞參數(shù)。組合繼承將原型鏈和借用構(gòu)造函數(shù)組合到一起,發(fā)揮兩者之長的一張繼承模式,下面來看個例子。組合繼承最大的問題是無論在什么情況下,都會調(diào)用兩次父類型構(gòu)造函數(shù)。 繼承 繼承是面向?qū)ο笳Z言中特別重要的概念,js的繼承主要是靠原型鏈實現(xiàn)的。 原型鏈!?。?看到我給標(biāo)題打了三個嘆號嗎,這里真的很重要!這里真的很重要!這里真的很重要!j...

    awkj 評論0 收藏0
  • 深入理解 JavaScript 中的 class

    摘要:在規(guī)范中,引入了的概念。使用中的聲明一個類,是非常簡單的事。中面向?qū)ο髮嵗谋澈笤?,實際上就是原型對象。與區(qū)別理解上述原理后,還需要注意與屬性的區(qū)別。實際上,在中,類繼承的本質(zhì)依舊是原型對象。 在 ES6 規(guī)范中,引入了 class 的概念。使得 JS 開發(fā)者終于告別了,直接使用原型對象模仿面向?qū)ο笾械念惡皖惱^承時代。 但是JS 中并沒有一個真正的 class 原始類型, clas...

    Vicky 評論0 收藏0

發(fā)表評論

0條評論

最新活動
閱讀需要支付1元查看
<