Kreiranje JavaScript objekta
U JavaScriptu se stalno susrećemo sa objektima. Ako ste pažljivo čitali sve tekstove do sada, videli ste da JavaScript ima neke ugrađene objekte koje možemo koristiti u programiranju. Tako smo naučili da radimo sa objektima Math, String, Array, Date i sl. koji nam prilično "olakšavaju život". Navedeni objekti su nam pre svega važni zbog svojih metoda (funkcija koje pripadaju objektu, eng. methods), ali objekat takođe može sadžati i podatke, odnosno svojstva (ili "atribute", eng. properties).
Znači objekat je jedan "konglomerat" podataka i funkcija, tj. svojstava i metoda. Ovde ćemo naučiti kako da napravimo sopstvene objekte u JavaScriptu.
Objektni literal
Za razliku od "pravih" objektno-orijentisanih jezika, u JavaScriptu se ne kreiraju klase za objekte, već se objekat izgrađuje prostim navođenjem njegovih svojstava i metoda.
Objektni literal se kreira pomoću vitičastih zagrada. Nemojte mešati ovako definisan objekat i telo funkcije - to su dve sasvim različite stvari. Kreiranje "praznog" objekta je moguće na sledeći način:
var obj = {};
Dodavanje svojstava i metoda ovako kreiranom (u stvari, bilo kom objektu) je zastrašujuće jednostavno - svojstvo/metod se samo navede u izrazu dodele vrednosti.
obj.svojstvo = vrednost;
obj.metod = function() {...};
Svojstva su praktično obične promenljive/reference. Lako je zaboraviti se i pokušati da se doda "svojstvo na svojstvo". Ovo je naravno moguće, ali ne bez kreiranja novog objekta na koji će svojstvo biti referenca.
obj.podobjekat = {};
obj.podobjekat.svojstvo = vrednost;
Isto tako, možemo definisati ceo objekat, sve sa svojstvima i metodima, u jednom koraku:
var obj = {
svojstvo: vrednost,
metod: function() {...},
...
};
Primetite da su svojstva unutar objektnog literala, data u obliku liste, odnosno da se odvajaju zarezom.
Ovo naravno ne znači da je objekat "finalizovan" i da se kasnije ne može proširiti dodavanjem novih svojstava/metoda. Kao što smo rekli, bilo kom objektu možemo naknadno dodati nova svojstva.
Skraćena sintaksa
Osim korišćenja funkcijskog izraza, moguće je definisati metode objekta i bez korišćenja ključne reči function. U tomslučaju se navodi samo naziv metoda, parametri u zagradama i telo funkcije unutar vitičastih zagrada.
var obj = {
...
metod() {...}
...
};
Ovim se ništa suštinski ne menja, samo je zapis malo kompaktniji.
Objektni literal
Hajde da prvo kreiramo jedan "prazan" objekat u koji ćemo potom dodati neka svojstva i metode.
var obj = {};
obj.ime = "Pero";
obj.prezime = "Kvržica";
obj.punoIme = function() {
console.log(this.ime + " " + this.prezime);
};
//...
obj.punoIme(); // pozivamo metod punoIme() - "Pero Kvržica"
obj.prezime = "Perić"; // menjamo vrednost svojstva prezime
obj.punoIme(); // opet pozivamo punoIme() - sada je rezultat "Pero Perić"
Dakle, kreirali smo objekat obj bez ijednog svojstva. Onda smo mu naknadno dodali svojstva ime i prezime koja sadrže string vrednosti. Dodali smo i svojstvo punoIme koje je referenca na anonimnu funkciju. Praktično, ovo svojstvo je metod.
Da bi metod pristupio svojstvima "sopstvenog" objekta, koristimo objekta this. Sećate se, da je ovaj objekat "kontekst" za koji se poziva funkcija, odnosno objekat iz koga je funkcija pozvana. Kada pozovemo funkciju kao metod objekta, samim tim taj objekat postaje kontekst funkcije, odnosno unutuar metoda, this pokazuje na objekat kome metod pripada.
Na kraju vidimo šta se dešava kada pozovemo funkciju (povezuje ime i prezime i ispisuje rezultat u konzoli web čitača), i šta se dešava kada menjamo vrednosti svojstava.
Definisanje celog objekta u literalu
Pogledajte sada kako kreiramo isti objekat od malopre, ali navođenjem liste svojstava unutar literala.
var obj = {
ime: 'Pero',
prezime: "Kvrzica",
punoIme: function() {
console.log (this.ime + " " + this.prezime);
}
};
Ovako definisan objekat funkcioniše isto kao i onaj u prvom primeru. Primetite kako su sada parovi svojstvo/vrednost dati kao lista (odvojeni zarezom).
Evo i istog primera, samo uz korišćenje skraćenog zapisa:
var obj = {
ime: 'Pero',
prezime: "Kvrzica",
punoIme() {
console.log (this.ime + " " + this.prezime);
}
};
Obratite pažnju sada na jednu vrstu greške koja može prilično da vas namuči:
obj.prezime = "Perić"; // promena vrednosti postojećeg svojstva
obj.przime = "Milić"; // dodavanje novog svojstva, zbog obične greške u kucanju
U pitanju je situacija sa promenom vrednosti svojstva, kao u prvom primeru. I zaista, najpre smo promenili vrednost svojstva prezime u "Perić". Međutim, u drugoj liniji smo napravili grešku u kucanju i zadali vrednost za nepostojeće svojstvo przime.
JavaScript ovo neće shvatiti kao grešku. Sećate se - kada se dodeli vrednost nepostojećem svojstvu, to svojstvo se prosto doda u objekat, pa će tako naš objekat od tog trenutka imati svojstva prezime i przime. Na taj način će naš program nastaviti da radi, ali ćemo dobijati pogrešne rezultate - može da se desi da grešku ni ne primetimo.
Objektni konstruktor
Alternativni način kreiranju objekta je korišćenje objekta Object kao konstruktora. Ovaj način zahteva korišćenje operatora new, koji se izvršava nad pozivom konstruktorske funkcije Object().
var obj = new Object();
...isto kao
var obj = {};
U nekom od kasnijih tekstova ćemo se baviti time kako da programiramo sopstvene konstruktorske funkcije koje nam služe za kreiranje objekata. Za sada je dovoljno da znamo da poziv koji smo naveli kreira nov, "prazan" objekat.
Objekat Object ima jako značajnu ulogu. Pre svega, njegov prototipski objekat je uvek na kraju lanca prototipskog nasleđivanja.
Objekat Object takođe poseduje neke fundamentalne metode za rad sa objektima i svojstvima. Ovo je takođe tema kojom ćemo se naknadno baviti. Jedan od tih metoda je i metod create(), koji predstavlja noviju alternativu za kreiranje objekta, ako želimo da izbegnemo konstruktorske funkcije:
var obj = Object.create();
Ovaj metod kreiranja objekta je uveden da bi se na jasniji način definisao lanac prototipskog nasleđivanja. Drugim rečima, kada kreiramo objekat pomoću literala, ili pomoću konstruktora Object(), takvi objekti direktno nasleđuju mogućnosti objekta Object. Ako želimo to da izbegnemo, tj. da formiramo "naš" lanac nasleđivanja, najlakše ćemo to postići korišćenjem metoda Object.create(). I ovo je nešto čime ćemo se kasnije podrobnije baviti.
Za sada je bitno da znamo samo da se na naveden način (metod Object.create() se poziva bez parametara), takođe kreira "prazan" objekat, koji direktno nasleđuje objekat Object.
Alternativni načini kreiranja objekta
Videćete da je sve isto kao i kada kreiramo objekat sa {}.
var obj = new Object();
obj.ime = "Pero";
obj.prezime = "Kvržica";
obj.punoIme = function() {
console.log(this.ime + " " + this.prezime);
};
To važi i za poziv metoda create().
var obj = Object.create();
obj.ime = "Pero";
obj.prezime = "Kvržica";
obj.punoIme = function() {
console.log(this.ime + " " + this.prezime);
};
U nekom od narednih tekstova ćemo videti kako je metod create() mnogo moćniji nego što smo ovde prikazali. Videćete kako se mogu zadati prototip objekta i lista svojstava.
- S. Stefanov, K.C. Sharma (2013): Object-Oriented JavaScript, 2nd Edition, Packt, Birmingham
- Mozilla Developer Network, Object Initializer