„JavaScript“ sukurti objektą - kaip apibrėžti objektus JS

Objektai yra pagrindinis į objektą orientuoto programavimo apimtis. Šiame straipsnyje aprašysiu kelis objektų kūrimo „JavaScript“ būdus. Jie yra:

  • Objektas pažodinis
  • Object.create ()
  • Užsiėmimai
  • Gamyklos funkcijos

Objekto pažodinis

Pirma, turime atskirti duomenų struktūras ir objektinius objektus. Duomenų struktūros turi viešus duomenis ir neturi jokio elgesio. Tai reiškia, kad jie neturi metodų.

Tokius objektus galime lengvai sukurti naudodamiesi tiesiogine objekto sintakse. Tai atrodo taip:

const product = { name: 'apple', category: 'fruits', price: 1.99 } console.log(product);

„JavaScript“ objektai yra dinamiškos raktų ir verčių porų kolekcijos. Raktas visada yra eilutė ir turi būti unikalus kolekcijoje. Vertė gali būti primityvus, objektas ar net funkcija.

Mes galime pasiekti nuosavybę naudodami taško arba kvadrato žymėjimą.

console.log(product.name); //"apple" console.log(product["name"]); //"apple"

Čia yra pavyzdys, kai vertė yra kitas objektas.

const product = { name: 'apple', category: 'fruits', price: 1.99, nutrients : { carbs: 0.95, fats: 0.3, protein: 0.2 } }

Nuosavybės vertė carbsyra naujas objektas. Štai kaip mes galime pasiekti carbsturtą.

console.log(product.nutrients.carbs); //0.95

Trumpų nuosavybių pavadinimai

Apsvarstykite atvejį, kai mūsų savybių vertės yra saugomos kintamuosiuose.

const name = 'apple'; const category = 'fruits'; const price = 1.99; const product = { name: name, category: category, price: price }

„JavaScript“ palaiko vadinamuosius trumpų savybių pavadinimus. Tai leidžia mums sukurti objektą naudojant tik kintamojo pavadinimą. Tai sukurs nuosavybę tuo pačiu pavadinimu. Kitas objektyvas pažodžiui prilygsta ankstesniam.

const name = 'apple'; const category = 'fruits'; const price = 1.99; const product = { name, category, price }

Object.create

Toliau pažiūrėkime, kaip įgyvendinti objektus elgesiu, objektinius objektus.

„JavaScript“ turi vadinamąją prototipo sistemą, leidžiančią dalytis objektais. Pagrindinė idėja yra sukurti objektą, vadinamą prototipu, turintį bendrą elgesį, ir tada jį naudoti kuriant naujus objektus.

Prototipo sistema leidžia mums sukurti objektus, kurie paveldi elgesį iš kitų objektų.

Sukurkime objekto prototipą, kuris leistų pridėti produktų ir iš pirkinių krepšelio gauti bendrą kainą.

const cartPrototype = { addProduct: function(product){ if(!this.products){ this.products = [product] } else { this.products.push(product); } }, getTotalPrice: function(){ return this.products.reduce((total, p) => total + p.price, 0); } }

Atkreipkite dėmesį, kad šį kartą turto vertė addProductyra funkcija. Ankstesnį objektą taip pat galime parašyti naudodami trumpesnę formą, vadinamą stenografijos metodo sintakse.

const cartPrototype = { addProduct(product){/*code*/}, getTotalPrice(){/*code*/} }

Tai cartPrototypeyra objekto prototipas, kuris išlaiko bendrą elgesį, kurį atspindi du metodai, addProductir getTotalPrice. Jis gali būti naudojamas kuriant kitus objektus, paveldinčius šį elgesį.

const cart = Object.create(cartPrototype); cart.addProduct({name: 'orange', price: 1.25}); cart.addProduct({name: 'lemon', price: 1.75}); console.log(cart.getTotalPrice()); //3

cartObjektas turi cartPrototypekaip savo prototipą. Tai paveldi iš jo elgesį. cartturi paslėptą ypatybę, nukreipiančią į objekto prototipą.

Kai mes naudojame metodą objekte, pirmiausia ieškoma paties objekto, o ne jo prototipo.

tai

Atkreipkite dėmesį, kad mes naudojame specialų raktinį žodį, thisnorėdami pasiekti ir modifikuoti objekto duomenis.

Atminkite, kad funkcijos yra nepriklausomi „JavaScript“ elgesio vienetai. Jie nebūtinai yra daikto dalis. Kai jie yra, turime turėti nuorodą, leidžiančią funkcijai pasiekti kitus to paties objekto narius. thisyra funkcijos kontekstas. Tai suteikia prieigą prie kitų savybių.

Duomenys

Jums gali kilti klausimas, kodėl mes neapibrėžėme ir inicializavome paties productsobjekto prototipo ypatybės.

Mes neturėtume to daryti. Prototipai turėtų būti naudojami dalytis elgesiu, o ne duomenimis. Dalinantis duomenimis, keli krepšelio objektai turės tuos pačius produktus. Apsvarstykite toliau pateiktą kodą:

const cartPrototype = { products:[], addProduct: function(product){ this.products.push(product); }, getTotalPrice: function(){} } const cart1 = Object.create(cartPrototype); cart1.addProduct({name: 'orange', price: 1.25}); cart1.addProduct({name: 'lemon', price: 1.75}); console.log(cart1.getTotalPrice()); //3 const cart2 = Object.create(cartPrototype); console.log(cart2.getTotalPrice()); //3

Tiek cart1ir cart2objektai paveldi bendrą elgesį nuo cartPrototypepat pasidalinti tuos pačius duomenis. Mes to nenorime. Prototipai turėtų būti naudojami dalytis elgesiu, o ne duomenimis.

Klasė

Prototipinė sistema nėra įprastas objektų statybos būdas. Kūrėjai labiau žino, kaip statyti objektus ne klasėse.

Klasės sintaksė leidžia labiau susipažinti su objektais, turinčiais bendrą elgesį. Tai vis tiek sukuria tą patį prototipą už scenos, tačiau sintaksė yra aiškesnė ir mes taip pat išvengiame ankstesnės su duomenimis susijusios problemos. Klasė siūlo konkrečią vietą apibrėžti kiekvieno objekto duomenis.

Čia yra tas pats objektas, sukurtas naudojant klasės cukraus sintaksę:

class Cart{ constructor(){ this.products = []; } addProduct(product){ this.products.push(product); } getTotalPrice(){ return this.products.reduce((total, p) => total + p.price, 0); } } const cart = new Cart(); cart.addProduct({name: 'orange', price: 1.25}); cart.addProduct({name: 'lemon', price: 1.75}); console.log(cart.getTotalPrice()); //3 const cart2 = new Cart(); console.log(cart2.getTotalPrice()); //0

Atkreipkite dėmesį, kad klasėje yra konstruktoriaus metodas, kuris inicializavo tuos duomenis, skirtingus kiekvienam naujam objektui. Konstruktoriaus duomenys nėra dalijami tarp egzempliorių. Norėdami sukurti naują egzempliorių, naudojame newraktinį žodį.

Manau, kad klasės sintaksė yra aiškesnė ir daugumai kūrėjų pažįstama. Nepaisant to, jis daro panašų dalyką, sukuria prototipą su visais metodais ir naudoja jį apibrėždamas naujus objektus. Su prototipu galima susipažinti naudojant Cart.prototype.

Pasirodo, kad prototipo sistema yra pakankamai lanksti, kad būtų galima taikyti klasės sintaksę. Taigi klasės sistemą galima imituoti naudojant prototipo sistemą.

Privačios nuosavybės

Vienintelis dalykas yra tai products, kad naujojo objekto nuosavybė pagal nutylėjimą yra vieša.

console.log(cart.products); //[{name: "orange", price: 1.25} // {name: "lemon", price: 1.75}]

Mes galime padaryti jį privatų naudodami maišos #priešdėlį.

Privačios nuosavybės deklaruojamos su #namesintakse. #yra pati nuosavybės pavadinimo dalis ir turėtų būti naudojama deklaruojant ir pasiekiant turtą. Čia yra deklaravimo productskaip privačios nuosavybės pavyzdys :

class Cart{ #products constructor(){ this.#products = []; } addProduct(product){ this.#products.push(product); } getTotalPrice(){ return this.#products.reduce((total, p) => total + p.price, 0); } } console.log(cart.#products); //Uncaught SyntaxError: Private field '#products' must be declared in an enclosing class

Gamyklos funkcijos

Kitas variantas yra sukurti objektus kaip uždarymų kolekcijas.

Uždarymas yra funkcijos galimybė pasiekti kintamuosius ir parametrus iš kitos funkcijos net tada, kai išorinė funkcija yra įvykdyta. Pažvelkite į cartobjektą, pastatytą naudojant vadinamąją gamyklos funkciją.

function Cart() { const products = []; function addProduct(product){ products.push(product); } function getTotalPrice(){ return products.reduce((total, p) => total + p.price, 0); } return { addProduct, getTotalPrice } } const cart = Cart(); cart.addProduct({name: 'orange', price: 1.25}); cart.addProduct({name: 'lemon', price: 1.75}); console.log(cart.getTotalPrice()); //3

addProductir getTotalPriceyra dvi vidinės funkcijos, pasiekiančios kintamąjį productsiš savo tėvų. Jie turi prieigą prie productskintamo įvykio, kai tėvas Cartįvykdo. addProductir getTotalPriceyra du uždarymai, turintys tą patį privatų kintamąjį.

Cart is a factory function.

The new object cart created with the factory function has the products variable private. It cannot be accessed from the outside.

console.log(cart.products); //undefined

Factory functions don’t need the new keyword but you can use it if you want. It will return the same object no matter if you use it or not.

Recap

Usually, we work with two types of objects, data structures that have public data and no behavior and object-oriented objects that have private data and public behavior.

Data structures can be easily built using the object literal syntax.

JavaScript offers two innovative ways of creating object-oriented objects. The first is using a prototype object to share the common behavior. Objects inherit from other objects. Classes offer a nice sugar syntax to create such objects.

Kita galimybė yra apibrėžti objektus - uždarymų kolekcijas.

Norėdami sužinoti daugiau apie uždarymus ir funkcijų programavimo metodus, peržiūrėkite mano knygų seriją „Funkcinis programavimas su„ JavaScript “ir„ React “.

Funkcinio programavimo“ „JavaScript“ knygoje pasirodys.