摘要:這幾天因?yàn)閷?duì)于中的作用域鏈和原型鏈有點(diǎn)混淆,當(dāng)訪問(wèn)一個(gè)不帶有修飾的變量時(shí),我想知道它的搜索順序,因?yàn)樽饔糜蜴湹逆溄Y(jié)點(diǎn)也是一個(gè)變量對(duì)象,那么當(dāng)在這個(gè)變量對(duì)象中查找變量時(shí)會(huì)不會(huì)沿著它的原型鏈查找呢這樣就有兩種可能先查找作用域鏈前端的變量對(duì)象,然
這幾天因?yàn)閷?duì)于JavaScript中的作用域鏈和原型鏈有點(diǎn)混淆,當(dāng)訪問(wèn)一個(gè)不帶有this修飾的變量時(shí),我想知道它的搜索順序,因?yàn)樽饔糜蜴湹逆溄Y(jié)點(diǎn)也是一個(gè)變量對(duì)象,那么當(dāng)在這個(gè)變量對(duì)象中查找變量時(shí)會(huì)不會(huì)沿著它的原型鏈查找呢?這樣就有兩種可能:
先查找作用域鏈前端的變量對(duì)象,然后再查找它的原型,然后再查找作用域鏈中下一個(gè)變量對(duì)象,然后再查找它的原型;
一直查找作用域鏈中的變量對(duì)象,直到window對(duì)象,再查找它的原型。
然而在使用with語(yǔ)句做實(shí)驗(yàn)時(shí),發(fā)現(xiàn)了下面的現(xiàn)象,因此本篇文章是我對(duì)下面的事實(shí)作出的猜測(cè)和理解,望指正!
考察下列代碼:
Object.prototype.s=10; (function(){ var s=25; var obj={}; obj.__proto__={}; obj.__proto__.__proto__={s:15}; with(obj){ console.log(s);//輸出15 } }());
上述代碼中,在Object.prototype中定義了一個(gè)屬性s=10,在匿名函數(shù)中定義一個(gè)變量s=25,其中又有一個(gè)對(duì)象obj,在obj的二級(jí)原型鏈中定義一個(gè)屬性s=15,然后,使用with將這個(gè)對(duì)象obj掛在作用域鏈頂端,輸出s,但是它輸出了15.
對(duì)此我做出的猜測(cè)是:在搜查變量中實(shí)際上是一個(gè)二維的過(guò)程而不是一維的,它構(gòu)造出的二維鏈?zhǔn)沁@樣子的:
所以上述過(guò)程中,先從obj(即作用域鏈頂端的變量對(duì)象開(kāi)始搜查),因?yàn)閛bj本身沒(méi)有s,則沿著obj的原型鏈搜查,在二級(jí)原型鏈中找到了s=15,從而停止搜查,返回s=15的值,故而輸出15.
按照這個(gè)思路,發(fā)現(xiàn)所有對(duì)象的原型鏈都最終指向Obje.prototype,所以為了驗(yàn)證這個(gè)猜想,做下述實(shí)驗(yàn),即刪除s=15這個(gè)語(yǔ)句
Object.prototype.s=10; //保留Object.prototype中的s (function(){ var s=25; var obj={}; obj.__proto__={}; obj.__proto__.__proto__={};//刪除了s:15 with(obj){ console.log(s);//輸出10 } }());
上述代碼輸出了10,這就是說(shuō),沿著第一個(gè)作用域鏈結(jié)點(diǎn)的原型鏈找,最終在Objec.prototype中找到了s,從而停止查找,那么函數(shù)中s=25沒(méi)有遍歷到
下面做個(gè)實(shí)驗(yàn),證明確實(shí)是二維查找。
使用嵌套的with語(yǔ)句,在作用域鏈頂端掛兩個(gè)對(duì)象,其中第二個(gè)對(duì)象是一個(gè)函數(shù)對(duì)象,而s正是在Function.prototype中,如果上面的猜想可行,那么應(yīng)該能正確輸出s,而事實(shí)上確實(shí)如此
Function.prototype.s=5;//給Funct.prototype添加s var obj={}; var func=function(){}; (function(){ var s=25; //s=25 with(func){ //嵌套 with(obj){ console.log(s); //輸出5 } } }());
上述輸出的正是5,其過(guò)程如下所示:
最后要特別說(shuō)明的是,函數(shù)對(duì)象本身和函數(shù)的上下文不是同一個(gè)東西,比如上圖中,我并不知道匿名函數(shù)上下文的__proto__指向哪里,但是我認(rèn)為它不會(huì)指向Function.prototype,因?yàn)槿绻鸉unction.prototype在匿名函數(shù)上下文的繼承鏈中,那么下面代碼應(yīng)該能正常輸出:
Function.prototype.s=5;//給Funct.prototype添加s var obj={}; (function(){ with(obj){ console.log(s); //輸出???? } }());
也就是說(shuō),因?yàn)閛bj本身沒(méi)有s,一直找到Object.prototype中也沒(méi)有s,轉(zhuǎn)而從作用域鏈的下一節(jié)點(diǎn)也即匿名函數(shù)上下文尋找,同時(shí)匿名函數(shù)中也沒(méi)有s,如果Function.prototype在匿名函數(shù)上下文的繼承鏈中,那么應(yīng)該能找到s=5,但是很遺憾,上面輸出的是
Uncaught ReferenceError: s is not defined。
若改成下面這樣則能正常輸出15,因?yàn)閟本身就在匿名函數(shù)的上下文中
Function.prototype.s=5;//給Funct.prototype添加s var obj={}; (function(s=15){ //參數(shù) with(obj){ console.log(s); //輸出15 } }());
文章版權(quán)歸作者所有,未經(jīng)允許請(qǐng)勿轉(zhuǎn)載,若此文章存在違規(guī)行為,您可以聯(lián)系管理員刪除。
轉(zhuǎn)載請(qǐng)注明本文地址:http://systransis.cn/yun/86934.html
摘要:如果此對(duì)象表示非靜態(tài)上下文中聲明的內(nèi)部類,則形參類型作為第一個(gè)參數(shù)包括顯示封閉的實(shí)例。參數(shù)字段名返回此類中指定字段的對(duì)象拋出如果找不到帶有指定名稱的字段。 一、類的加載 1. 概述 當(dāng)程序要使用某個(gè)類時(shí),如果該類還未被加載到內(nèi)存中,則系統(tǒng)會(huì)通過(guò)加載,連接,初始化三步來(lái)實(shí)現(xiàn)對(duì)這個(gè)類進(jìn)行初始化 2. 加載 就是指將class文件讀入內(nèi)存,并為之創(chuàng)建一個(gè)Class對(duì)象 任何類被使用時(shí)系統(tǒng)都...
摘要:的正則表達(dá)式體系是參照建立的。字面量形式構(gòu)造函數(shù)形式以上都是創(chuàng)建了一個(gè)內(nèi)容為的正則表達(dá)式,其表示對(duì)一個(gè)手機(jī)號(hào)碼的校驗(yàn)。按照給定的正則表達(dá)式進(jìn)行替換,返回替換后的字符串。 正則表達(dá)式,也稱規(guī)則表達(dá)式,經(jīng)常使用其來(lái)完成對(duì)字符串的校驗(yàn)和過(guò)濾。由于正則表達(dá)式的靈活性、邏輯性和功能性都非常強(qiáng)大,而且 可以利用很簡(jiǎn)單的方式完成對(duì)復(fù)雜字符串的控制,所以很多程序語(yǔ)言都支持正則表達(dá)式。在JavaScri...
摘要:驗(yàn)證驗(yàn)證階段的主要目的是為了確保文件的字節(jié)流中包含的信息符合當(dāng)前虛擬機(jī)的要求,并且不會(huì)危害虛擬機(jī)自身的安全。不同的虛擬機(jī)對(duì)類驗(yàn)證的實(shí)現(xiàn)可能會(huì)有所不同,但大致都會(huì)完成以下四個(gè)階段的驗(yàn)證文件格式的驗(yàn)證元數(shù)據(jù)的驗(yàn)證字節(jié)碼驗(yàn)證和符號(hào)引用驗(yàn)證。 原文地址 虛擬機(jī)把描述類的數(shù)據(jù)從Class文件加載到內(nèi)存,并對(duì)數(shù)據(jù)進(jìn)行校驗(yàn),轉(zhuǎn)換解析和初始化,最終形成可以被虛擬機(jī)直接使用的Java類型,Thisis ...
摘要:廣州三本大三在讀,在廣州找實(shí)習(xí)。這篇文章其實(shí)主要是記錄一下自己的面試經(jīng)歷,希望大家看完之后能有所了解進(jìn)入中小公司究竟需要什么水平。時(shí)間復(fù)雜度盡量低一些使用快排的,將給出的隨機(jī)數(shù)做基準(zhǔn)值返回的坐標(biāo)就是了。 前言 只有光頭才能變強(qiáng) 這陣子跑去面試Java實(shí)習(xí)生啦~~~我來(lái)簡(jiǎn)單介紹一下背景吧。 廣州三本大三在讀,在廣州找實(shí)習(xí)。大學(xué)開(kāi)始接觸編程,一個(gè)非常平庸的人。 在學(xué)習(xí)編程時(shí),跟我類似的人應(yīng)...
摘要:規(guī)范目的為提高團(tuán)隊(duì)協(xié)作效率便于后臺(tái)人員添加功能及前端后期優(yōu)化維護(hù)輸出高質(zhì)量的文檔特制訂此文檔。 規(guī)范目的 為提高團(tuán)隊(duì)協(xié)作效率, 便于后臺(tái)人員添加功能及前端后期優(yōu)化維護(hù), 輸出高質(zhì)量的文檔, 特制訂此文檔。 文件規(guī)范 文件命名規(guī)則 文件名稱統(tǒng)一用小寫的英文字母、數(shù)字和下劃線的組合,其中不得包含漢字、空格和特殊字符;命名原則的指導(dǎo)思想一是使得你自己和工作組的每一個(gè)成員能夠方便的理解每一個(gè)...
閱讀 1305·2023-04-25 19:33
閱讀 1185·2021-10-21 09:39
閱讀 3658·2021-09-09 09:32
閱讀 2636·2019-08-30 10:58
閱讀 1648·2019-08-29 16:17
閱讀 892·2019-08-29 15:29
閱讀 2906·2019-08-26 11:55
閱讀 2672·2019-08-26 10:33