PHP v objetí objektů (2)

23. 7. 2001
Doba čtení: 4 minuty

Sdílet

V dnešním pokračování nás čekají definice konstruktoru a metod. Vytvoříme také první skutečný objekt.

Minule jsme začali vytvářet třídu Menu, dnes v tom budeme pokračovat.

Konstruktor

Dalším krokem bude definice metod. Každá třída by měla (ale nemusí!) obsahovat jednu speciální metodu, která se nazývá konstruktor. Konstruktor je metoda, která má stejný název jako samotná třída. Její kód se automaticky spouští při vytváření nového objektu, je proto velice vhodná pro různé inicializační algoritmy. Náš konstruktor bude přebírat jeden (nepovinný) parametr – pole položek menu (klíčem je název odkazu, hodnotou pak URL). Defaultně se konstruktoru předá prázdné pole.

class Menu {
  # definice atributů...

  function Menu($polozky = array()) {
    reset($polozky);
    while (list($nazev, $url) = each($polozky)) {
      $this->nazvy[] = $nazev;
      $this->adresy[] = $url;
    }
  }
} 

Metoda vypadá stejně jako obyčejná funkce, až na to, že je napsána uvnitř definice třídy.

Asi jste si všimli zvláštního identifikátoru $this. Když definujeme třídu, ještě nevíme, jak se budou různé instance (konkrétní objekty) jmenovat. Uvnitř definice třídy proto používáme $this, což znamená něco jako „tento objekt“ – PHP pochopí, že chceme přistupovat k atributům objektu, se kterým právě pracujeme. Použití identifikátoru $this je povinné. Kdybychom jej vynechali a psali pouze $polozky = $pole (jako se to může dělat třeba v C++), hodnota parametru $pole by se uložila do lokální proměnné $polozky metody Menu() a ne do atributu objektu.

Objekt

V tomto okamžiku už máme vytvořenou plnohodnotnou třídu, kterou můžeme instanciovat neboli vytvořit podle ní skutečný objekt:

$hlavni_menu = new Menu(array('Úvod'  => 'index.html',
                              'Obsah' => 'toc.html',
                  'Jedna' => '1.html'));

$dalsi_menu = new Menu();
  # nebo: $dalsi_menu = new Menu; 

K vytvoření nové instance objektu slouží operátor new. Za ním následuje název třídy a v závorkách seznam parametrů, které se předají konstruktoru. Pokud konstruktoru nepředáváte žádný argument, můžete dokonce závorky za názvem třídy vynechat. V ukázce jsme vytvořili dva objekty: $hlavni_menu a $dalsi_menu. Každý má své vlastní hodnoty atributů, jak se můžete přesvědčit pomocí tohoto kódu:

$hlavni_menu->podklad = "#33FF33";
print 'Hlavní menu: ' . $hlavni_menu->podklad . '. ';
print 'Další menu: ' . $dalsi_menu->podklad . '.'; 

První print vytiskne číslo barvy "#33FF33", kdežto druhý standardní hodnotu  "#FFFF00".

Poznámka: K vytvoření objektu není definice konstruktoru třídy nutná. Jinými slovy třídy, podle kterých se pomocí operátoru new vytvářejí objekty, nemusí mít žádný konstruktor. Je ale dobré, když ho mají.

Metody

Prozatím nám to, jak Menu vypadá, nepřináší nic převratného. Objekty bez metod specifikujících jejich chování jsou takřka k ničemu. Je to jenom obyčejný datový typ záznam, k jehož implementaci žádné objekty nepotřebujeme – vystačili bychom si s asociativními poli. Pojďme tedy Menu nějak vylepšit:

class Menu {
  # definice atributů a konstruktoru...

  # vložení nové položky menu
  function vloz($nazev, $url) {
    $this->nazvy[] = $nazev;
    $this->adresy[] = $url;
  }

  # zobrazení jedné položky menu
  function zobrazPolozku($x) {
    print '<A HREF="' . $this->adresy[$x] . '">'
       . $this->nazvy[$x] . '</A><BR>';
  }

  # vypsání menu na stránku
  function zobraz() {
    print '<TABLE BGCOLOR="' . $this->podklad . '" BORDER=0>';
    print '<TR><TD>';
    for ($x = 0; $x < count($this->adresy); $x++) {
      $this->zobrazPolozku($x);
    }
    print '</TD></TR></TABLE>';
  }
}

$hlavni_menu = new Menu();
$hlavni_menu->vloz('Obsah', 'toc.html');
$hlavni_menu->vloz('Jedna', '1.html');
$hlavni_menu->zobraz(); 

Vytvořili jsme další tři metody. Funkce vloz() vkládá do menu novou položku. Metoda zobraz() je v celé třídě nejvýkonnější. Postará se o vytvoření menu na WWW stránce. K tomu volá také další metodu, zobrazPolozku(). Důvod, proč jsem pro takovou jednoduchou akci vytvořil novou metodu, se vyjeví v některém z dalších pokračování.

Metody objektů se volají stejně, jako se přistupuje k atributům: za název objektu umístíme operátor -> a jméno volané metody (viz kód).

Proměnná $this se v metodách nahrazuje objektem, pomocí kterého jsme metody volali. (V tomto případě objektem $hlavni_menu.) Kdybychom provedli:

$dalsi_menu = new Menu;
$dalsi_menu->vloz('Odhlásit', 'logout.php'); 

nahrazovalo by se $this v metodě vloz() objektem $dalsi_menu.

No a tady je kompletní třída Menu:

class Menu {
  var $polozky;             # pole položek menu
  var $podklad = '#FFFF00'; # barva pozadí

  # konstruktor
  function Menu($pole = array()) {
    reset($polozky);
    while (list($nazev, $url) = each($polozky)) {
      $this->nazvy[] = $nazev;
      $this->adresy[] = $url;
    }
  }

  # vložení nové položky menu
  function vloz($nazev, $url) {
    $this->nazvy[] = $nazev;
    $this->adresy[] = $url;
  }

  # zobrazení jedné položky menu
  function zobrazPolozku($x) {
    print '<A HREF="' . $this->adresy[$x] . '">'
       . $this->nazvy[$x] . '</A><BR>';
  }

  # vypsání menu na stránku
  function zobraz() {
    print '<TABLE BGCOLOR="' . $this->podklad . '" BORDER=0>';
    print '<TR><TD>';
    for ($x = 0; $x < count($this->adresy); $x++) {
      $this->zobrazPolozku($x);
    }
    print '</TD></TR></TABLE>';
  }
} 

Poznámka: U názvů atributů, stejně jako u ostatních proměnných PHP, záleží na velikosti písmen v identifikátorech. Atributy $obj->Hodnota a $obj->hodnota jsou tedy dva různé prvky.

Není tomu tak ale u názvů samotných tříd a metod. Třídy Trida a trIDA jsou pořád jedna a tatáž, stejně jako metody mojeMetoda() a MojeMETODA().

bitcoin_skoleni

Trochu nezvyklé pravidlo, není-liž pravda? Pozor na něj!

Pokračování příště…

Autor článku

Michal Burda vystudoval informatiku a aplikovanou matematiku a nyní pracuje na Ostravské univerzitě jako odborný asistent. Zajímá se o data mining, Javu a Linux.