Hlavní navigace

PHP v objetí objektů (6)

Michal Burda 20. 8. 2001

Dnešním dílem náš seriál o objektově orientovaném programování v PHP dokončíme. Popíšeme si standardní funkce PHP pro práci s objekty a zamyslíme se nad zvyklostmi, které by měl OOP programátor v PHP dodržovat.

Další funkce

Kromě mechanismu tříd nabízí PHP ještě několik funkcí, které vám práci s objekty mohou zpříjemnit. Všechny jsou popsány v manuálu k PHP, proto zde jen v rychlosti:

 Funkce      Návratová hodnota     Popis
get_class($objekt)  řetězec   Funkce vrací název třídy, jejíž instancí je objekt $objekt.
get_parent_class($objekt)   řetězec   Funkce vrací název předka (parent class) třídy, jejíž instancí je objekt $objekt.
get_class_methods($nazev_tridy)     pole řetězců     Funkce vrací pole názvů metod třídy, jejíž název je předán v řetězcovém argumentu $nazev_tridy. Pole obsahuje názvy všech dostupných metod, tedy i metod zděděných.
get_class_vars($nazev_tridy)    pole řetězců     Funkce vrací pole názvů deklarovaných atributů třídy, jejíž název je předán v řetězcovém argumentu $nazev_tridy. Pole obsahuje názvy všech atributů deklarovaných pomocí var (i zděděných).
get_object_vars($objekt)    asociativní pole   Funkce vrací asociativní pole atributů objektu $objekt. (Klíč = název atributu)
is_subclass_of($objekt, $rodicovska_trida)  bool    Funkce vrací true, jestliže objekt $objekt je instancí třídy, která je podtřídou třídy specifikované řetězcem $rodicovska_trida. Jinak vrátí false (i tehdy, je-li $objekt instancí třídy $rodicovska_trida!).
class_exists($nazev_tridy)  bool    Funkce vrátí true, jestliže třída daná řetězcem $nazev_tridy existuje. Jinak vrátí false.
method_exists($objekt, $nazev_metody)   bool    Funkce vrátí true, jestliže objekt $objekt disponuje metodou s názvem $nazev_metody. Jinak vrátí false.
get_declared_classes()  pole řetězců     Funkce vrátí pole názvů deklarovaných tříd. V některých verzích PHP může vracet i názvy některých speciálních tříd -- viz manuál k PHP.
call_user_method($nazev_metody, $objekt, $parametry...)     různé     Funkce zavolá na objekt $objekt metodu s názvem $nazev_metody a předá jí případné $parametry.... Vrací hodnotu získanou z výsledku volání dané metody. 

Názvy tříd a metod vracené těmito funkcemi jsou vždy automaticky převedeny na malá písmena abecedy.

Dobré mravy

Chcete-li v PHP psát objektově, musíte více než kde jinde pamatovat na dobré mravy a nutit se psát čitelně. PHP, narozdíl od C++ či Javy, neprovádí žádné kontroly typů a chybu v syntaxi rozezná, až když na ni při zpracování narazí. To je zdrojem mnoha nepříjemných chyb, které se špatně hledají, a části z nich se vyvarujete, budete-li důsledně dodržovat jisté konvence a úmluvy.

Zcela byste se měli vyvarovat statických volání metod tříd uvnitř jiné třídy za jiným účelem, než je volání předefinované funkce – ve 4. části jste mohli vidět, jaké psí kusy to dělá s proměnnou  $this.

Všechny atributy, které chcete používat, byste měli důsledně deklarovat v sekci var definice třídy a nespoléhat se na skutečnost, že v případě neexistence třídního atributu vytvoří PHP atribut objektu.

Také byste si měli vytvořit nějaké konvence pojmenovávání. Proč si neodskočit do Javy:

  • názvy tříd – psát dohromady, každé slovo názvu začíná velkým písmenem (např.  MujUkazkovyNazevTridy)
  • názvy metod – psát dohromady, první písmeno každého slova kromě prvního velké (např.  nejakaMetoda())
  • názvy atributů – psát malými písmeny, slova oddělovat podtržítkem (např.  $nejaky_atribut)

Váš kód se tak stane čitelnějším a přehlednějším.

PHP neumožňuje skrývání (pomocí konstrukcí private jako v C++ či Javě), a to přináší další nepříjemnosti. Dobrým zvykem proto může být předsazování podtržítka '_' před atributy a metody, které nejsou určeny k použití z vnějšku. Lehce tak dáte uživateli vašich tříd (nebo sami sobě) najevo, které metody se mohou používat přímo a které ne.

Někteří programátoři si zvykli na pravidlo nepřistupovat z vnějšku k atributům objektů přímo, ale vytvářet speciální metody k tomu určené:

/*
implementace jednoducheho seznamu zbozi ve
virtualnim obchode
*/
class SeznamZbozi {
  var $_nazev_seznamu; # nazev seznamu zboží
  var $_pocet;         # pocet položek, jen ke čtení!
  var $_polozky;       # pole položek

  # metody pro práci s názvem seznamu
  function vlozNazev($novy_nazev) {
    $this->_nazev_seznamu = $novy_nazev;
  }

  function vratNazev() {
    return $this->_nazev_seznamu;
  }

  # metoda pro práci s atributem $pocet
  function vratPocet() {
    return $this->_pocet;
  }

  # ...další metody
} 

Ke každému atributu definujte dvojici metod vloz... a vrat... (nebo anglicky set... a get...) a k atribitu přistupujte vyhradně jejich prostřednictvím. Má to hned dvě výhody. Za prvé, položkám, které chcete mít z vnějšku nepřístupné nebo jen ke čtení, uvedené metody nenapíšete nebo napíšete jenom verzi vrat  – a tak ihned vidíte, co si ke kterému atributu můžete dovolit. Druhou výhodou je možnost přidat později k ukládání nebo čtení hodnoty atributu nejaké akce navíc.

Například chcete pro ladicí účely vědět o každém zápisu hodnoty do atributu $_nazev_seznamu. Jednoduše upravíte metodu  vlozNazev():

function vlozNazev($novy_nazev) {
  print 'Pozor! Změna názvu seznamu!';
  print ' Stará hodnota: ' . $this->_nazev_seznamu;
  print ' Nová hodnota: ' . $novy_nazev;
  $this->_nazev_seznamu = $novy_nazev;
} 

Nebo po čase zjistíte, že atribut $pocet naší třídy SeznamZbozi je zbytečný, tak ho odstraníte a metodu vratPocet() přepíšete:

function vratPocet() {
  return count($this->_polozky);
} 

Vše bez nebezpečí, že vám zbytek kódu, který třídu SeznamZbozi používá, přestane fungovat.

Závěr

Jak sami vidíte, programovat objektově v PHP lze. Otázkou však zůstává, nakolik je to příjemné a výhodné. Dostanete do rukou silné nástroje jako dědičnost a polymorfizmus, ale na druhou stranu špatným stylem programování si zavlečete do kódu mnoho nepříjemných chyb. Absence jakýchkoliv kontrol typů je zde citelnou nevýhodou. Pro někoho nezvyklé vlastnosti operátoru přiřazení stejně jako nulová podpora pro abstraktní třídy a nezabezpečené volání předefinovaných metod, to všechno je matoucí a bývá zdrojem chyb. A tak odpověď na otázku, zda PHP s OOP ano, či ne, zůstává jako vždy jen a jen na vás.

Našli jste v článku chybu?

3. 3. 2010 16:41

riki (neregistrovaný)

vitaj o 9 rokov dopredu :)

29. 1. 2010 10:31

Andrej (neregistrovaný)

Asi je tento „tutorial“ uz nejaky cas na webe, lebo ako autor uvadza „… PHP neumožňuje skrývání (pomocí konstrukcí private jako v C++ či Javě), a to přináší další nepříjemnosti…“.
PHP uz nejaku dobu prava k atributom poskytuje, ci sa mylim?


DigiZone.cz: Česká televize mění schéma ČT :D

Česká televize mění schéma ČT :D

Vitalia.cz: Říká amoleta - a myslí palačinka

Říká amoleta - a myslí palačinka

Podnikatel.cz: Přehledná titulka, průvodci, responzivita

Přehledná titulka, průvodci, responzivita

Root.cz: Vypadl Google a rozbilo se toho hodně

Vypadl Google a rozbilo se toho hodně

Lupa.cz: Slevové šílenství je tu. Kde nakoupit na Black Friday?

Slevové šílenství je tu. Kde nakoupit na Black Friday?

Lupa.cz: Není sleva jako sleva. Jak obchodům nenaletět?

Není sleva jako sleva. Jak obchodům nenaletět?

DigiZone.cz: Sony KD-55XD8005 s Android 6.0

Sony KD-55XD8005 s Android 6.0

120na80.cz: Jak oddálit Alzheimera?

Jak oddálit Alzheimera?

Měšec.cz: Kdy vám stát dá na stěhování 50 000 Kč?

Kdy vám stát dá na stěhování 50 000 Kč?

Lupa.cz: Avast po spojení s AVG propustí 700 lidí

Avast po spojení s AVG propustí 700 lidí

Lupa.cz: Babiš: E-shopů se EET možná nebude týkat

Babiš: E-shopů se EET možná nebude týkat

Vitalia.cz: Láska na vozíku: Přitažliví jsme pro tzv. pečovatelky

Láska na vozíku: Přitažliví jsme pro tzv. pečovatelky

Vitalia.cz: Chtějí si léčit kvasinky. Lék je jen v Německu

Chtějí si léčit kvasinky. Lék je jen v Německu

Podnikatel.cz: Prodává přes internet. Kdy platí zdravotko?

Prodává přes internet. Kdy platí zdravotko?

Podnikatel.cz: EET: Totálně nezvládli metodologii projektu

EET: Totálně nezvládli metodologii projektu

Měšec.cz: Jak vymáhat výživné zadarmo?

Jak vymáhat výživné zadarmo?

Lupa.cz: Proč firmy málo chrání data? Chovají se logicky

Proč firmy málo chrání data? Chovají se logicky

Lupa.cz: Google měl výpadek, nejel Gmail ani YouTube

Google měl výpadek, nejel Gmail ani YouTube

Měšec.cz: Zdravotní a sociální pojištění 2017: Připlatíte

Zdravotní a sociální pojištění 2017: Připlatíte

Vitalia.cz: Jsou čajové sáčky toxické?

Jsou čajové sáčky toxické?