A JavaScript prototípusos öröklődésének megismerése

Öröklődés

Az öröklődés az a folyamat, amelynek segítségével egy objektum egy másikra épülhet. Ez lehetővé teszi, hogy az objektumok megosszák egymás tulajdonságait.

Elkészítettem a Hero prototípust, és létrehoztam vele egy új superman nevű objektumot. De ezzel az objektummal nem csinálunk semmit. Ezért gondoskodjunk erről úgy, hogy létrehozunk egy másik függvényt dialogue néven.

function dialogue() {
console.log('I am ' + this.name);
}

De ha most futtatjuk a kódunkat, semmi sem fog történni, mert ez a függvény nem tudja, hogy valójában mi a név. Ehhez arra van szükségünk, hogy

Az új függvénynek ugyanazokkal a tulajdonságokkal kell rendelkeznie, mint a Hero-nek. Ahelyett, hogy leírnánk őket ebben a függvényben, egyszerűen megmondhatjuk a JavaScriptnek, hogy örökítse őket a Hero prototípusából.

Ez a prototype tulajdonság segítségével lehetséges, amely bármely objektumon belül elérhető a JavaScriptben.

Azzal, hogy a dialogue-t a Hero.prototype-re helyeztük, elérhetővé tettük a Hero minden példánya számára.

Differenciális öröklés

A JavaScript egy másik öröklési modellel is rendelkezik, amelyet “differenciális öröklésnek” nevezünk. Ebben a modellben a metódusok nem másolódnak át a szülőből a gyermekbe. De ehelyett van egy kapcsolat a gyerekek és a szülő objektum között.

Itt a superman-nek valójában nincs saját dialogue() nevű metódusa. De akkor hogyan működik a superman.dialogue()?

Amikor a JavaScript motor a kódban találkozik a superman.dialogue() metódussal, a superman objektumon belül a dialogue nevű tulajdonságot keresi. Ha nem talál ilyet, akkor a prototípusláncban a superman Hero.prototype szülőjéhez, Hero.prototype-hez keres felfelé. Ott megtalálja a Hero.prototype.dialogue-t, és meghívja azt egy this-tel, amely a superman-hez van kötve.

Object.create()

Ezt még exkluzívabbá tehetjük azzal, hogy létrehozunk egy új osztályt a Superman számára, amely örökli a Hero prototípus tulajdonságait. Ezt úgy tehetjük meg, hogy a Superman prototípusát hozzárendeljük a Hero prototípusához, így:

function Superman() {}
Superman.prototype = Hero.prototype

De ez csak annyit tesz, hogy a Superman és a Hero osztályokat egyenlővé teszi. Amire valójában szükségünk van, az egy új objektum, amely a Hero prototípuson alapul. Az ES5 óta a JavaScript rendelkezik egy beépített függvénnyel, amelynek neve Object.create(). Használjuk itt az alábbiak szerint:

Superman.prototype = Object.create(Hero.prototype);

Ez létrehoz egy új üres objektumot, amely a Hero prototípuson alapul, és hozzárendeli a Superman prototípushoz. Így a Hero prototípusban lévő összes tulajdonságunkat elérhetjük a Superman prototípusban. Tehát ahelyett, hogy a new Hero-t hívnánk, hívhatjuk a new Superman-t, és minden úgy fog működni, ahogyan kell.

De ha jobban megnézzük a kimenetet, észrevehetjük, hogy van benne egy undefined. Ez azért van, mert jelenleg a Hero csak önmagának konstruktora. A Hero tulajdonságait a Superman prototípuson belül kell call megadni.

function Superman() {
Hero.call(this, 'Superman', 'Clark Kent', 'Krypton')
}

Hozzunk létre egy másik konstruktort MarvelMovies néven az alábbiak szerint:

function MarvelMovies(movieName, releaseYear) {
this.movieName = movieName;
this.releaseYear = releaseYear;
}

Amikor egy függvényt konstruktorként használunk, a this az általunk létrehozott új objektumra utal. Ebben a konstruktorban tehát movieName és releaseYear argumentumokat vettem, és ezeket az értékeket a avengers nevű új MarvelMovies példányunk movieName és releaseYear tulajdonságaihoz rendeltem.

var avengers = new MarvelMovies("avengers", 2012);

Ezután létrehozok egy új, output nevű metódust ehhez a prototípushoz az alábbiakban látható módon:

MarvelMovies.prototype.output = function() {
return "Movie: " + this.movieName + " Released in " + this.releaseYear;
}
console.log(avengers.output());

Jövőbeni öröklés

Az öröklés igazán nagyszerű aspektusa, hogy a JavaScript lehetővé teszi, hogy egy osztály tulajdonságait még azután is módosítsuk vagy bővítsük, hogy már definiáltuk.

A JavaScript megnézi a prototípust, amikor megpróbáljuk elérni egy objektum tulajdonságait. Tehát futás közben is módosíthatjuk az osztályokat!

Az alábbiakban látható módon hozzunk létre egy tömböt ennek szemléltetésére:

var numbers = ;
Array.prototype.shuffle = function() {
return this.sort(function() {
return Math.round( Math.random() * 2) - 1;
});
};
console.log(numbers.shuffle());

Itt a numbers tömb már a Array.prototype.shuffle előtt is létezett. De a JavaScriptben a tulajdonságok keresése felfelé halad a prototípus-láncban. Ezért a tömb még mindig hozzáférést kap az új shuffle metódushoz, mivel a Array.prototype-nél létezik, amikor ténylegesen megpróbáljuk használni.

Egyszerűen fogalmazva, létrehoztunk egy tömböt, majd visszamentünk és minden tömbnek hozzáférést adtunk egy új metódushoz.

Vélemény, hozzászólás?

Az e-mail-címet nem tesszük közzé.