在JS 中, 有兩條鍊子,作用域鍊和原型鏈,作用域鏈相對容易理解點,而原型鏈就相對複雜了,我們今天就來詳細的講講這複雜的原型鏈以及原型繼承。我們直接進入正題吧!
作用域鏈
作用域鏈相對容易理解,兩點
1、函數限定變數作用域,就是說,在JavaScript中,在函數裡面定義的變量,可以在函數裡面被訪問,但是在函數外無法訪問
2、在JavaScript中使用變量,JavaScript解釋器首先在目前作用域中搜尋是否有該變數的定義,如果有,就是用這個變數;如 果實沒有就到父域中尋找該變數. 由於變數提升,因此在實際開發的時候,推薦將變數都寫在開始的地方,也就是在函數的開頭將變數就定義好.
接著再來看看原型鏈
##原型鏈
在Javascript 中, 每個###物件
o 都有 proto #屬性(這個屬性在IE9 以下沒有暴露出來),被稱為原型,根據屬性搜尋原則 物件o 可以通過.或者 [] 讀取原型的屬性,但是當寫入時,不會在原型上修改屬性,而是直接在物件o 上添加.當然,原型也是物件,原型也有proto 屬性, 子子孫孫無窮無盡也~~~
真的是無窮無盡嗎,當然不是!
var obj = {a: 'pawn'};
上面透過物件字面值的方式申明了一個物件 obj,並且擁有屬性a .
#由於 o.proto === Object.prototype,那麼可以認為這種方式等價於
var obj = new Object({a: 10});
所以,o 是繼承自 Object .prototype,但 Object.prototype 也是物件,它繼承自什麼呢?
##好吧,它繼承自null , 萬劍歸宗。 好了,現在找到了原型鏈的第一個子鏈
#我們來看 functionvar func = function() {}
透過字面上值宣告一個function
同理## func 繼承自Function.prototype,那 Function.prototype 也是物件,它繼承自什麼呢?
############可以看到,Function.prototype 繼承自Object.prototype,這也就回到了上一條鍊子.###############好了,那現在引入一個問題,Function 本身也是函數,那 Function繼承自哪呢? 當然是 Function.prototype,所以JS中最亂倫的東西出現了,Function 是自己的老子,即#########################那 Object 也是函數,Object 也當然繼承自Function.prototype ##################好了,這就是所有原型鏈的東西######看起來好像很亂,盜JK老師一張圖,詳細說明這個問題############现在做一个总结
1、所有的函数都继承自 Function.prototype,Function,Object 是函数,所以继承自 Function.prototype
2、所有的对象都直接或间接继承自 Object.prototype,Function.prototype.proto === Object.prototype函数也是对象,所以函数最终继承自Object.prototype .
3、Object.prototype 继承自 null,万剑归宗
原型继承
看完了原型链,再看原型继承就简单了
var ProtoHerite = function(source) { var o = {}; if(o.proto){ o.proto = source; return o; } var F = function() {}; F.prototype = source; return new F(); }
这个函数返回的对象原型继承自 source,这也是 Object.create(source) 实现思路.
原型链继承固然很强大,但是也有一些问题,比如共享的原型属性容易被修改,在创建子类型的实例时,不能向超类传参数,等等。
以上是js中的作用域鍊和原型鏈以及原型繼承的詳細內容。更多資訊請關注PHP中文網其他相關文章!