oop v javascriptu! část 1:prototyp

Ahoj přátelé😀
Když jsem se učil Javascript, vždy jsem přemýšlel, když definuji řetězec nebo funkci atd.. Jak je možné získat některé vlastnosti a metody, jako je délka nebo vyhledávání nebo pro každý nebo jiné metody? Když se podíváme do zákulisí, uvědomíme si, odkud to všechno pochází. Konečně se dozvíme něco málo o oop v javascriptu a o tom, co se přesně děje pod kapotou.
Takže prozkoumáme oop v javascriptu ve dvou částech. První část bude o prototypu a nastavení pro oop a druhá část je jen o oop v javascriptu.
Javascript je objektově založený jazyk založený na prototypech na rozdíl od jiných jazyků, které jsou založeny na třídách.
To způsobuje, že hierarchie a dědičnost objektů Javascript jsou trochu divné a složité. Ale co přesně jsou prototypy?
Začněme naši cestu jednoduchým příkladem:


Zde jsem deklaroval objekt a zaprotokoloval jeho tři vlastnosti, Ale počkejte chvíli! Právě jsem deklaroval vlastnost jména a věku, kde sakra je ta metoda hasOwnProperty (vlastnost objektu, což je funkce zvaná metoda) pocházející? Hmmm...🤔 zaprotokolujeme celý objekt samotný, abychom viděli, co obsahuje:


Dobře, dobře, podívejte se, kdo je tady, teď vidíme, když definujeme objekt, javascript mu dává skrytou, ale přístupnou vlastnost, kterou je objekt a nazývá se proto . Nyní se podívejme na proto _ vlastnost:


Zde můžeme vidět metodu hasOwnPropert a také některé další metody. Zajímavé je, že pokud definujeme tisíce objektů s miliony vlastností, ve všech bude stále ještě jedna výchozí vlastnost, kterou je tento objekt se všemi těmito metodami a tento objekt nazvaný 'Global object prototype' a co víc zajímavé je, že javascript nebude tento objekt definovat nebo jinými slovy duplikovat pro každý objekt, který definujeme, pouze jim poskytne proto vlastnost, která odkazuje na prototyp globálního objektu a jinými slovy zdědí prototyp globálního objektu, takže zajistí, že nevybuchne paměť a mnohem zajímavější je, když se podíváme na prototyp globálního objektu, má proto samotný majetek! Ačkoli je to nula a je to druh odkazu na slepou uličku, jde o to, že neexistuje žádný objekt, který by neměl proto . Javascript je plný zajímavých věcí :)
Pojďme proto prozkoumat různými způsoby:

Objektový literál pomocí metod object.create a object.setPrototypeOf

*1. pomocí object.create:* **

Máme tedy objekt Car se třemi vlastnostmi nebo metodami a ničím jiným. Poté jsme deklarovali proměnnou tesla a přiřadili ji k object.create se 2 parametry, což je objekt Car a druhý parametr je objekt s vlastností name a hodnotou tesla (je to jednoduchý objekt, ale s jiným tvarem definice uvnitř object.create), Zaznamenejme proměnnou tesla a uvidíme, co objekt object.create dělá:


Jak vidíme, object.create definuje objekt s vlastností name a hodnotou tesla pomocí druhého parametru a proto tohoto objektu se odkazuje na objekt, který jsme zadali v prvním parametru object.create (což je v tomto příkladu objekt Car) a proto objektu Car se odkazuje na prototyp globálního objektu a proto na globální objekt se označuje jako null.
řetězení prototypu objektů
Pamatujte si, že všechny prototypy jsou propojeny, bez ohledu na to, jak budou vnořené, na konci dojde ke globálnímu prototypu objektu a poté k nule a tomu se říká řetězení prototypu objektu.
druhá proměnná, kterou jsme definovali, je detail, pojďme to zaprotokolovat:


Je to objekt se svou speciální vlastností zvanou rychlost a hodnotou 3001 a jeho proto se označuje jako tesla, jak můžete uhodnout z příkladu obrázku, a proto tesla se označuje jako objekt Car a proto objekt Car se označuje jako prototyp globálního objektu. a to je řetězení prototypu.

Prototypové delegování
pokud příkladu věnujete větší pozornost, můžete vidět, že detail může přistupovat k vlastnosti name objektu tesla a objektu auta, ale tesla nemůže mít přístup k vlastnosti rychlosti detailu a je to proto, že mohou mít přístup nebo dědit pouze objekty, které se odkazuje na jejich prototypy. a je to vztah shora dolů nazývaný Prototypální delegování.

takže když zalogujeme tesla.speed, javascript ho bude hledat uvnitř objektu tesla a pokud ho nenajde, bude ho hledat uvnitř svého proto, což je objekt Car, a pokud žádná taková vlastnost neexistuje, bude hledat dál je to uvnitř jiného proto v řetězci prototypů, což je prototyp globálního objektu, a pokud tam taky není, dá nám to nedefinované.

Důvod nepříjemné chyby známé jako „** není funkce“
Jak jsem vysvětlil výše, když javascript nemůže najít vlastnost uvnitř řetězce prototypu, vrátí nedefinovaný. Pokud však vlastnost speed byla funkce (metoda) místo čísla a javascript ji nemůže najít, vrátí chybu 'tesla.speed is not a function' .

takže když voláme nějaké metody na polích nebo funkcích a javascript je nemůže najít, vrátí chybu a jsem si jistý, že jste byli v takové situaci, kdy se předtím stále zobrazuje „* není funkce“.
třetí proměnná nazvaná volvo bude mít stejný proces jako tesla a rozdíl mezi volvo a tesla je jen hodnota vlastnosti názvu je volvo:

*2.using object.setPrototypeOf:* **

tři proměnné (tesla,detail,volvo), které jsme definovali výše, lze definovat pomocí metody object.setPrototypeOf():


V tomto případě použití definujeme objekt s jeho speciální vlastností a hodnotou. Poté první parametr object.setPrototypeOf vybere objekt, na který chceme manipulovat s jeho protoreferencí, a druhý parametr je objekt, na který chceme, aby se na něj proto odkazovalo.

Na obrázku výše tedy vybereme tesla a nastavíme její proto referenci na objekt Car, vybereme objekt detailu a nastavíme jeho proto na objekt tesla a poté objekt volvo objekt na objekt Car.

Funkce konstruktoru pomocí nového klíčového slova

Funkce jsou funkce a objekt!
Funkce se mohou chovat jako objekt, protože když je definujeme, javascript jim dá spoustu metod a vlastností, a jak můžete vidět, definoval jsem funkci Car a dal jí name property.

Nyní prozkoumáme výše uvedený obrázek:

Když existuje funkce, jejíž název je velký a má uvnitř klíčové slovo ‚this‘, říkáme javascriptu, že se jedná o objekt a lze jej vytvořit pomocí nového klíčového slova. Vložením ‚toto‘ do funkce konstruktoru sdělíme javascriptu, že každý objekt, který vytvořil instanci z této funkce ‚toto‘, bude označován jako tento objekt.

Ve výše uvedeném příkladu je definování tesla pomocí nového klíčového slova a funkce Car() a ' this.name ' uvnitř funkce Car něco jako „hele javascript, tesla by měla mít vlastnost name a její hodnota by měla být jakákoliv, kterou předá jako argument, stejně jako volvo.“

Funkce auta se nazývá funkce konstruktoru.

Hej, chyběl nám ten prototypový díl, co s tím????🤔

Ve výše uvedeném příkladu manipulujeme s proto objektem Car. Takže když se Car stane referenčním prototypem jakéhokoli objektu, bude to objekt obsahující ty metody, které jsme dali prototypu Car.
Všimněte si, že jméno není v proto objektu, jméno je něco, co musíme dát každému objektu, který jsme definovali s jeho speciální hodnotou.
Pojďme přihlásit teslu a podívat se na výsledek:


Když jsme vytvořili instanci Car jako tesla, vytvořili jsme objekt s názvem property a value tesla a jeho proto se odkazuje na Car prototype, což je objekt se třemi metodami, které jsme definovali a tento objekt se označuje jako globální prototyp objektu. stejný proces platí pro Volvo.

A teď hlavní důvod, proč máme prototypy?
Představte si, že chceme deklarovat tisíce objektů s vlastností name a některé metody, které by všechny měly mít, a všechny tyto metody dělají totéž, co metody jiných objektů.
Myslíte si, že je dobrý nápad deklarovat všechny tyto objekty jeden po druhém a definovat všechny tyto metody jednu po druhé pro každý objekt? Sakra ne! to zabije paměť.

pomocí funkce konstruktoru a prototypů stačí deklarovat jeden objekt se všemi metodami, které potřebujeme, a nechat ostatní objekty tyto metody zdědit a používat je.

ve výše uvedeném příkladu nedeklarujeme objekt volvo a objekt tesla a každý z nich třemi metodami, pouze vytvoříme instanci Car a zdědíme z něj metody.

a ano! Prototyp globálního objektu je jeden prototypový objekt obsahující metody pro všechny objekty v javascriptu.

rozdíl mezi proto a prototypu
Zašli jsme tak daleko, nenechám vás s touto otázkou bez odpovědi. I když už jste si možná všimli rozdílu.
Prototyp pouze existuje ve funkci a je definován jako vlastnost, když je funkce deklarována. Prototyp je pouze objekt metod, které dáváme funkci konstruktoru jako referenci pro proto objektu instance. .


jak můžeme vidět Car.prototype je stejná tesla.proto , protože tesla je instancí třídy Car a její proto se odkazuje na Car.prototype.

Třídy ES6 používající nové klíčové slovo
Nyní se dostáváme blíže k oblasti oop... V mnoha programovacích jazycích máme koncept nazývaný oop nebo objektově orientované programování, což je paradigma pro navrhování programů pomocí tříd a objektů.
Třídy jsou zavedeny v ES6 a umožňují Javascriptu používat oop, ale jen to předstírá a dělá to jako oop, ale pod kapotou je to úplně jiné a javascript používá stejný prototypový proces, o kterém jsme již věděli. Jinými slovy, javascript má oop, ale svým vlastním způsobem:)
Nyní se podívejme na proces prototypu s třídami a novými syntaxemi, abychom lépe porozuměli tomu, jak oop vypadá a jak probíhá prototyp a proces dědičnosti:


Deklaroval jsem třídu s názvem Car a uvnitř této třídy máme konstruktor. Toto je stejná funkce konstruktoru, kterou jsme viděli dříve:


A metody, které jsme deklarovali ve třídě Car, jsou jako bychom nastavili prototyp Car na některé metody, ale snadněji a čistěji:


Nyní si promluvme o této části:


Klíčové slovo „nové“ a jeho funkce již znáte.

Vytvoří instanci Car a vytvoří nový objekt s vlastností name a hodnotou tesla a objekt proto, který se odkazuje na objekt obsahující tyto tři metody, které jsme deklarovali ve třídě Car a další proto objekt, který je odkazován na globální prototyp objektu… totéž pro volvo.

Poté deklarujeme další třídu nazvanou Detail s její speciální vlastností pojmenovanou speed a pomocí extends a super() zdědíme všechny věci uvnitř třídy Car včetně vlastnosti name a proto objektu tří metod.

Zde je výsledek protokolování objektu detail, který je vytvořen z objektu Car:

Takto implementuje javascript oop :)

Dozvěděli jsme se o prototypu a o tom, co to je a jak jej můžete využít mnoha různými způsoby v javascriptu.

V další části prozkoumáme čtyři pilíře oop a všechny věci, které potřebujeme vědět, s příklady z reálného světa a kódu.

Do dalšího dílu Sbohem a hodně štěstí🤞