JS?class語法糖的深入剖析
引言
在很早以前,寫過一篇文章 “類”設(shè)計模式和“原型”設(shè)計模式——“復制”和“委托”的差異 ,大致意思就是說:代碼復用,也就是繼承、重寫,有兩種思路:1. 面向?qū)ο蟮念惱^承;2. 基于 JavaScript 原型鏈的原型繼承;前者的主要特點是:復制,通俗來說就是把變量、屬性再復制一份,后者的主要特點是:委托,通過屬性的查找來實現(xiàn)的。
后來呢,深入了解 JavaScript 高級程序設(shè)計中的繼承,包括構(gòu)造函數(shù)繼承、原型繼承、組合繼承、寄生組合繼承,都有各自的缺點,有興趣的朋友,可以看我這篇文章。
還有,本瓜特別記住:維基對 JavaScript 起源的解釋
JavaScript的語言設(shè)計主要受到了Self(一種基于原型的編程語言)和Scheme(一門函數(shù)式編程語言)的影響。在語法結(jié)構(gòu)上它又與C語言有很多相似。
最后,我的小結(jié)呢就是:JavaScript 本身的設(shè)計就是“通過原型委托”來實現(xiàn)代碼復用的,結(jié)果 ES6 搞出了個 class 作為語法糖,其本身還是基于原型鏈,但又是為了實現(xiàn)面向?qū)ο?,面向?qū)ο笫腔?class 類那種“復制”來實現(xiàn)代碼復用。
類 和 原型,是兩種不同的東西,JS class 將二者混在了一起,別不別扭?
后來也看到一些文章說在 JS 中使用 class 類會造成一些困擾,所以更加堅定要減少使用 class 。
而實際上,本篇題目是:JS class 并不只是簡單的語法糖,所以,本篇并不是為了說它不好,而是要說它的好的!
來吧,展翅!
class 第一個好:私有變量
如果不用 class , 還有什么更優(yōu)雅的方法實現(xiàn)以下子類的私有變量嗎?
class Person { constructor(firstName, lastName) { this.firstName = firstName; this.lastName = lastName; } // Person.constructor get FullName () { return this.firstName + " " + this.lastName; } } // Person class Employee extends Person { #salary; constructor(firstName, lastName, salary) { super(firstName, lastName); this.salary = salary; } get salary() { return this.#salary; } set salary(salary) { this.#salary = salary; console.log("Salary changed for " + this.fullName + " : $" + this.salary); } } // Employee
設(shè)想下,我們用原型鏈的思路模擬(對象):
const Person = { set givenName(givenName) { this._givenName = givenName; }, set familyName(familyName) { this._familyName = familyName; }, get fullName() { return `${this._givenName} ${this._familyName}`; } }; const test = Person; // 這里假設(shè)用 對象 模擬 類 test.givenName = "Joe"; test.familyName = "Martinez"; console.log("test.fullName", test.fullName); // Joe Martinez console.log("test.givenName", test.givenName); // undefined console.log("test._givenName", test._givenName); // Joe
沒有實現(xiàn)私有屬性 _givenName
而 class 可以將值存為私有,使得對象外部不能修改:
class 第二個好:super 繼承
class 可以通過 super 更優(yōu)雅的實現(xiàn)繼承、和重寫,比如:
class Cash { constructor() { this.total = 0; } add(amount) { this.total += amount; if (this.total < 0) this.total = 0; } } // Cash class Nickles extends Cash { add(amount) { super.add(amount * 5); } } // Nickles
如果是按照老樣子,原型鏈,它可能是這樣的:
const Cash = function() { this.total = 0; }; // Cash Cash.prototype = { add : function(amount) { this.total += amount; if (this.total < 0) this.total = 0; } }; // Cash.prototype const Nickles = function() { Object.assign(this, new Cash()); this.add = function(amount) { Cash.add.apply(this, amount); }; } // Nickles
讀起來有點亂,this 指來指去,還有在構(gòu)造函數(shù)中手動做的 assign 操作,這會增加代碼執(zhí)行耗時。
綜上兩點,JS class 還是非常有使用它的價值的,不用逃避,把它用在合適的場景,肯定會發(fā)現(xiàn)其魅力~~
以上就是JS class語法糖的深入剖析的詳細內(nèi)容,更多關(guān)于JS class語法糖的資料請關(guān)注腳本之家其它相關(guān)文章!
相關(guān)文章
lodash內(nèi)部方法getData和setData實例解析
本篇章我們將了解lodash里內(nèi)部關(guān)于Data的操作方法,重點關(guān)注getData、setData兩個內(nèi)部方法,同時由實現(xiàn)上引申其他內(nèi)部封裝的方法,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進步,早日升職加薪2022-08-08讓chatGPT教你如何使用taro創(chuàng)建mbox
這篇文章主要為大家介紹了讓chatGPT教你如何使用taro創(chuàng)建mbox實現(xiàn)實例詳解,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進步,早日升職加薪2023-03-03微信小程序 轉(zhuǎn)發(fā)功能的實現(xiàn)
這篇文章主要介紹了微信小程序 轉(zhuǎn)發(fā)功能的實現(xiàn)的相關(guān)資料,這里提供實現(xiàn)方法及實例幫助大家學習理解,需要的朋友可以參考下2017-08-08一文了解JavaScript用Element?Traversal新屬性遍歷子元素
這篇文章主要介紹了一文了解JavaScript用Element?Traversal新屬性遍歷子元素,文章圍繞Element?Traversal新屬性的相關(guān)資料展開詳細內(nèi)容,需要的朋友可以參考一下,希望對大家有所幫助2021-11-11