Forum und email

Osztályok, objektumok (PHP 4-ben)

Table of Contents

class

Az osztály (objektumtípus) változók és rajtuk műveletet végző függvények [metódusok] együttese. Osztályt az alábbi szintakszis szerint lehet definiálni:

<?php
class Kosar {
    var 
$dolgok;  // A kosárban levő dolgok

    // berak a kosárba $db darabot az $sorsz indexű dologból

    
function berak($sorsz$db) {
        
$this->dolgok[$sorsz] += $db;
    }

    
// kivesz a kosárból $db darabot az $sorsz indexű dologból

    
function kivesz($sorsz$db) {
        if (
$this->dolgok[$sorsz] > $db) {
            
$this->dolgok[$sorsz] -= $db;
            return 
true;
        } elseif (
$this->dolgok[$sorsz] == $db) {
            unset(
$this->dolgok[$sorsz]);
            return 
true;
        } else {
            return 
false;
        }
    }
}
?>

Ez definiál egy Kosar nevű osztályt, ami a kosárban levő áruk asszociatív tömbjéből áll, és definiál 2 funkciót hozzá, hogy bele lehessen rakni, illetve kivenni a kosárból.

Warning

Egy osztálydefiníciót NEM szedhetsz szét több fájlra. Szintén NEM darabolhatsz egy osztálydefiníciót több PHP blokkra, hacsak nem egy metódus közepén teszed ezt valamilyen oknál fogva. A következő példakód tehát működésképtelen:

<?php
class teszt {
<?
php
?>
    function teszt() {
        print 'oké';
    }
}
?>

Ez viszont rendben van:

<?php
class teszt {
    function 
teszt() {
        
?>
        <?php
        
print 'oké';
    }
}
?>

Az alábbi figyelmeztetések a PHP 4-es verziójára érvényesek.

Caution

Az stdClass név le van foglalva, mivel belsőleg a Zend motor használja. Emiatt nem lehet egy stdClass nevű osztályod PHP-ben.

A __sleep és __wakeup nevek speciálisak a PHP osztályokban. Nem szabad ezeket a neveket használni a metódusokhoz, hacsak nem a hozzájuk tartozó speciális funkcionalitást szeretnéd felülírni. Lásd az alábbi részletes leírást.

A PHP számára lefoglalt az összes __ karakterekkel kezdődő metódusnév, mint speciális név. Nem szabad __ karakterekkel kezdődő metódusnevet adni, hacsak nem a dokumentált funkciókat szeretnéd használni.

PHP 4-ben csak állandó értékű var inicializáló értékek megengedettek. Ha nem állandó értéket szeretnél beállítani, írnod kell egy inicializáló metódust, ami automatikusan meghívódik, amikor egy objektumpéldány létrejön az osztályból. Az ilyen metódusokat hívjuk konstruktoroknak (lásd lentebb).

class Kosar {
    /* Egyik alábbi értékadás sem működik PHP 4-ben */
    var $mai_datum = date("Y. m. d.");
    var $nev = $csaladi_nev;
    var $tulajdonos = 'Ferenc ' . 'János';
    /* Ámde tömböt konstans elemekkel megadhatunk */
    var $termekek = array("Videó", "TV");
}

/* Így kell a fenti beállításokat elérni */
class Kosar {
    var $mai_datum;
    var $nev;
    var $tulajdonos;
    var $termekek = array("Videó", "TV");

    function Kosar() {
        $this->mai_nap = date("Y. m. d.");
        $this->nev = $GLOBALS['csaladi_nev'];
        /* stb. . . */
    }
}
?>

Az osztályok típusok, vagyis az aktuális változók tervrajzai. A kívánt típusú változót a new operátorral hozhatod létre.

<?php
$kosar 
= new Kosar;
$kosar->berak("10"1);

$masik_kosar = new Kosar;  
$masik_kosar->berak("0815"3);  
?>

Ez létrehozza a Kosar objektumosztály $kosar és $masik_kosar nevű objektumpéldányait. A $kosar objektum berak() függvényét meghívtuk, hogy a 10-es számú árucikkből rakjon 1 darabot a kosárba. Három darab 0815 számú ternék került a $masik_kosar nevű kosárba.

Mind a $kosar, mind a $masik_kosar objektumoknak megvannak a berak() és kivesz() metódusai, és tulajdonságai. Ezek azonban egymástól független metódusok és tulajdonságok. Az objektumokról hasonlóan gondolkozhatsz, mint a könyvtárakról az állományrendszerben. Lehetséges, hogy két különböző OLVASSEL.TXT állományod van, ha ezek két különböző könyvtárban vannak. Úgy mint a könytáraknál, ahol meg kell adnod a teljes elérési utat, hogy egy állományra szeretnél hivatkozni a gyökérkönyvtárban, a teljes metódusnevet meg kell adnod, hogy meg tudd azt hívni. A PHP nyelvben a gyökérkönyvtár analógiája a globális környezet, és az elérési út elválasztója a ->. Ezért a $kosar->dolgok név és a $masik_kosar->dolgok név két különböző változót ad meg. Figyeld meg, hogy a változót $kosar->dolgok néven kell elérni, és nem $kosar->$dolgok néven, azaz a PHP változók neveibe csak egy dollárjelet kell tenned.

<?php
// helyes, egy dollárjel
$kosar->dolgok = array("10" => 1);

// helytelen, mivel a $kosar->$dolgok értelme $kosar->""
$kosar->$dolgok = array("10" => 1);

// helyes, de lehetséges, hogy nem a megcélzott eredmény
// $kosar->$valtozo értelme $kosar->dolgok
$valtozo dolgok;
$kosar->$valtozo = array("10" => 1);
?>

Egy osztály definiálásakor nem tudhatod, milyen néven lesz majd elérhető az objektumod a PHP programban: a Kosar osztály készítése idején nem volt ismert, hogy később $kosar vagy $masik_kosar néven nevezzük-e majd az objektumpéldányt. Ezért nem használhatod a Kosar osztályban a $kosar->dolgok hivatkozást. De hogy el tudjad érni az osztály saját metódusait és tulajdonságait az objektumpéldány nevétől függetlenül, használhatod a $this kvázi-változót, amit 'a sajátom' vagy 'az aktuális objektumpéldány' értelemben alkalmazhatsz. Ezért a '$this->dolgok[$sorsz] += $db' úgy olvasható, hogy 'adj $db darab $sorsz sorszámú terméket a saját dolgok tömbömhöz', vagy 'adj $db darab $sorsz sorszámú terméket az aktuális objektumpéldány dolgok tömbjéhez'.

Note: A $this néven futó kvázi-változó statikusan hívott osztálymetódusok esetében nincs jelen. Ez alól kivétel az az eset, amikor statikusan hívjuk meg a metódust egy példányosított objektumon belülről. Ez esetben a $this a meghívó objektumra fog hivatkozni. Ezt mutatja be szemléletesebben az alábbi példa:

<?php
class {
    function 
ize() {
        if (isset(
$this)) {
            echo 
'$this definiálva van (';
            echo 
get_class($this);
            echo 
")\n";
        } else {
            echo 
"\$this nincs definiálva.\n";
        }
    }
}

class 
{
    function 
bigyo() {
        
A::ize();
    }
}

$a = new A();
$a->ize();
A::ize();
$a = new B();
$b->bigyo();
B::bigyo();
?>

A fenti példa a következő kimenetet adja:

$this definiálva van (a)
$this nincs definiálva.
$this definiálva van (b)
$this nincs definiálva.

Note: Van pár hasznos függvény az osztályok és objektumok kezeléséhez. Lásd az Osztály és objektum függvények című részt.