摘要:返回一個對象先說一個最常用的方法構造函數獲取所有節點獲取節點的長度作用于鏈式調用測試上面的代碼就可以實現的效果因為我沒讀過源碼。
es5版本:(過兩天寫es6 版本的)
由淺入深地講,
先說使用,
function person(age, sex) { this.age = age; this.sex = sex; this.clothes = []; } person.prototype.addCloud = function(cloth) { this.clothes.push(cloth); } // 給對象增加增添服裝的方法 var a = new person(18, 0); // a = {age: 18, sex: 0, clothes: []}, a 現在就是一個18歲的小女孩了 var b = new person(19, 1); // b = {age: 19, sex: 1, clothes: []}, b 現在就是一個19歲的小男孩了 a.addCloud("redCloth") // a = {age: 18, sex: 0, clothes: ["redCloth"]},a新添 紅色衣服
以上內容是原型最簡單的使用,相當于構造一個對象,person被稱為構造函數,new person()被稱為實例化,a,b被稱為實例對象 稍微增加點難度
person.prototype.sayHello = function(word) { console.log( "I am " + this.age + "years old!" + word); } a.sayHello("nice to meet you"); //I am 18years old!nice to meet you
這里輸出了a的一個屬性age; 再增加一點難度,插個題外話,講一下this 的指向問題。 這里調用實例對象的age,在聲明方法的時候,是用的this。剛剛增添衣服的時候,也是用的this,原因是因為a調用的這個方法,要是寫一個
var c = a.sayHello; c("nice to meet you") //I am undefinedyears!nice to meet you 那么如果想像剛剛一樣的執行效果有以下四種方法 1.window.age = a.age; 2.c.bind(a)("nice to meet you"); 3.c.call(a, "nice to meet you"); 4.c.apply(a, ["nice to meet you"]);
稍微增加點難度,實現一個jQuery的效果; 以前經常有人問為什么JQ不能混搭原生js寫,這里也將作出解答。
測試
上面的代碼就可以實現jquery 的效果(因為我沒讀過jquery 源碼。所以就不胡亂判斷jquery 是不是也用這個原理)
說一下為什么jq 不能和 原生js 混搭用
從上面的內容不難看出,$之后返回的是一個實例化對象,而不是一個或多個節點。所以實際上我們并不是直接去操作節點,而且通知這個實例化對象,這個對象再去處理的節點。
上面click之后有一個return this , 這個是鏈式調用的核心。所謂的鏈式調用,表面上是一個個調用下去,比如
$().click(1).click(2)
實際上可以理解為 click完成后 返回到 $ ,然后再去click ,也就是
$().click(1) =>返回 $() 然后=> $().click(2);
如果再深入一點說
$()創建$對象 -> 對象$.click(1)執行1中事件并拋出執行結果---$對象 -> click(1)拋出的結果$對象再去執行click(2)的事件,并拋出執行結果---$對象
上面講了創造一個對象,下面說一原型鏈
原型鏈這方面有兩個關鍵詞 __proto__ 以及 prototype
前者是針對于實例化對象的,后者是針對于構造函數的
寫成代碼
function test() {} new test().__proto__ == test.prototype; //true
這個如果說到內存層次的話,就是他兩公用的一個內存,如果有很多實例化對象的話,就是他們__proto__的指針都指向這塊內存地址。
這里有一個知識點。
一個對象,如果自身屬性里面沒有,就會去 __proto__屬性里面去搜索
就跟員工一樣,有房子住自己房子,沒房子就住集體宿舍。自己買了高配電腦就用自己的,沒買就用公司的低配電腦。實例化對象.__proto__就像員工瞅瞅公司有啥公用物品,構造函數.prototype就是公司給員工購買啥公用物品, 所以實例化對象.__proto__ 也就和 構造函數.prototype指向一塊了
所以 即便test 已經實例化了。如果 test.prototype增加一個屬性, 實例化的test依舊會獲得這個屬性。
function test() {} var x = new test(); console.log(x.age) // undefined test.prototype.age = 5; console.log(x.age) // 5
如果代碼寫成這樣
function test() {} var x = new test(); console.log(x.age) // undefined test.prototype.age = 5; x.age = 10; console.log(x.age) // 10
所以 x.age 實際上搜索的是 x.__proto__.age
話都說到這份上了,我就隨便聊下繼承吧。
最簡單的繼承,合二為一。
function test() {} test.prototype.age = 5; function newTest() {} newTest.prototype = new test(); new newTest().age//5
講下這個繼承的原理。 剛剛說過了
一個對象,如果自身屬性里面沒有,就會去 __proto__屬性里面去搜索
那么new NewTest()的__proto__也就是 new test();
new Newtest()里面沒有的,就去__proto__里面(new test())里面找
new test()沒有的就去new test()的 __proto__里面找,然后就找到了test的prototype
當然這個繼承他是沒有靈魂的,因為test變化了newTest 也會變。
call繼承,一次性產品
function test() { this.sex = 0; } function newTest() { this.sex = 1; test.call(this); } new newTest().sex//0
call 我以前對他有過很多的理解,后來終于想到了一個最簡單的理解,就是洗腦,而且是強制性的,有的替換,沒有的,送你;
call的常用方法 func.call(小a, func參數);
func 大熱天跑到了小a家里,問小a 有沒有扇子,借過來扇了扇之后,對小a說他的扇子太破,他這邊有個新的,強制塞給了小a,并收取了小a兩塊錢
寫成代碼
function func(money) { console.log(this.fan); this.fan= "new_fan"; this.money -= money; console.log(this.fan); } var obj_a = { money: 10, fan: "pretty_fan" } func.call(obj_a, 2); console.log(obj_a); //pretty_fan //new_fan //{money: 8, fan: "new_fan"}
繼續聊繼承,call 這個繼承也是不怎么有靈魂的繼承,說白了就是把別人的東西都替換成自己的東西,別人沒有的,給別人,弄不好還被套路一波。但是繼承不到prototype里面的。
有一個繼承用Object.create()去繼承。。。
這個看上去比上面的高檔不少,實際上也沒什么用;
互不干擾式繼承
這個就顯得比較有靈魂,因為單純繼承,而且還不會被干擾 c = JSON.parse(JSON.stringify(new test())); 因為會拷貝不到里面不可遍歷的屬性 所以再合并一下之前的__proto__就行了。 newTest.prototype = Object.assign(new test().__proto__, c);
至于其他各種花里胡哨的繼承,網上一查一堆,我就不多介紹了,反正也就是花架子而已
文章版權歸作者所有,未經允許請勿轉載,若此文章存在違規行為,您可以聯系管理員刪除。
轉載請注明本文地址:http://m.specialneedsforspecialkids.com/yun/105144.html
摘要:對象詳解對象深度剖析,深度理解對象這算是醞釀很久的一篇文章了。用空構造函數設置類名每個對象都共享相同屬性每個對象共享一個方法版本,省內存。 js對象詳解(JavaScript對象深度剖析,深度理解js對象) 這算是醞釀很久的一篇文章了。 JavaScript作為一個基于對象(沒有類的概念)的語言,從入門到精通到放棄一直會被對象這個問題圍繞。 平時發的文章基本都是開發中遇到的問題和對...
摘要:接下來我們來聊一下的原型鏈繼承和類。組合繼承為了復用方法,我們使用組合繼承的方式,即利用構造函數繼承屬性,利用原型鏈繼承方法,融合它們的優點,避免缺陷,成為中最常用的繼承。 JavaScript是一門面向對象的設計語言,在JS里除了null和undefined,其余一切皆為對象。其中Array/Function/Date/RegExp是Object對象的特殊實例實現,Boolean/N...
摘要:設計模式是以面向對象編程為基礎的,的面向對象編程和傳統的的面向對象編程有些差別,這讓我一開始接觸的時候感到十分痛苦,但是這只能靠自己慢慢積累慢慢思考。想繼續了解設計模式必須要先搞懂面向對象編程,否則只會讓你自己更痛苦。 JavaScript 中的構造函數 學習總結。知識只有分享才有存在的意義。 是時候替換你的 for 循環大法了~ 《小分享》JavaScript中數組的那些迭代方法~ ...
摘要:在使用的過程中,通過操作符為對象添加新屬性是很常見的操作。但是,這個操作的結果實際上會受到原型鏈上的同名屬性影響。通過它,可以做到操作符做不到的事情,比如為對象設置一個新屬性,即使它的原型鏈上已經有一個的同名屬性。 在使用JavaScript的過程中,通過=操作符為對象添加新屬性是很常見的操作:obj.newProp = value;。但是,這個操作的結果實際上會受到原型鏈上的同名屬性...
摘要:函數式編程前端掘金引言面向對象編程一直以來都是中的主導范式。函數式編程是一種強調減少對程序外部狀態產生改變的方式。 JavaScript 函數式編程 - 前端 - 掘金引言 面向對象編程一直以來都是JavaScript中的主導范式。JavaScript作為一門多范式編程語言,然而,近幾年,函數式編程越來越多得受到開發者的青睞。函數式編程是一種強調減少對程序外部狀態產生改變的方式。因此,...
閱讀 2573·2023-04-25 18:13
閱讀 795·2021-11-22 12:10
閱讀 2988·2021-11-22 11:57
閱讀 2148·2021-11-19 11:26
閱讀 2183·2021-09-22 15:40
閱讀 1475·2021-09-03 10:28
閱讀 2711·2019-08-30 15:53
閱讀 1960·2019-08-30 15:44