ugrás a tartalomhoz

Egyke ősosztály PHP-ben

inf · 2010. Júl. 27. (K), 14.58

Egyke (singleton) ősosztály írása PHP-ben nem is olyan egyszerű, mint elsőre gondolná az ember. Több buktatója is van az ilyen osztály létrehozásának, ezért gondoltam, hogy írok róla pár sort.

Elég sűrűn használom az egyke mintát a most leírt örökléssel. Jobb szeretem így, mint gyár (factory) mintával kombinálva, persze ízlések és pofonok. Az örökléses megoldásnak annyi a hátulütője, hogy nem lehet szabadon megválasztani az ősosztályt, mindig az egyke (vagy annak leszármazottja) kell, hogy legyen.

Az egyik buktató amibe beleütközik az ember az osztály létrehozásakor, hogy a ReflectionClass úgy működik, mintha mi írtuk volna PHP-ben. Ha például reflectionnel akarunk elérni osztályon belülről egy privát metódust, akkor hibát dob. Ez nem túl szerencsés, mert a call_user_func() és call_user_func_array() leváltására teljesen jó lenne a reflection, viszont ilyen jogkörökkel használhatatlan.

Konkrétan az új példány paraméterezésénél lenne a reflectionre szükség. A problémát sajnos nem lehet megoldani, a konstruktort meg nem lehet publicra tenni, mert akkor az instance osztályfüggvényen kívülről is lehetne példányosítani.

class A
{
	static public function instance()
	{
		$reflection=new ReflectionClass(__CLASS__);
		$reflection->newInstanceArgs(array());
	}
	protected function __construct(){}
}
A::instance(); //Fatal Error

A probléma sajnos megoldhatatlan, a PHP fejlesztői nem tartják hibának, így marad a paraméterek nélküli példányosítás.

A másik buktató a statikus tulajdonságok és függvények öröklésével kapcsolatos. Ha egy statikus függvényt a szülőből örököl egy osztály, akkor abban a statikus változók a szülő statikus változóira mutatnak. A PHP fejlesztői szerint ez teljesen rendben van, szerintem nem.

In fact static method calls are resolved at compile time. When using an explicit class name the method is already identified completely and no inheritance rules apply.

Itt sem érdemes meddő vitát folytatni, ez van, ezt kell szeretni.


class A
{
	static public $i=0;
	static public function i()
	{
		self::$i=1;
	}
}
class B extends A{}

A::i();
echo 'A::$i='.A::$i; //A::$i=1
echo '<br>';
echo 'B::$i='.B::$i; //B::$i=1 (0 helyett)

Ez a probléma hál' Istennek áthidalható úgy, hogy csinálunk egy mapet azokkal az osztályokkal és példányokkal, amiket vissza akarunk hívni az instance osztályfüggvény hívásakor. A leszármazottban az instance hívásakor a mapet az ősosztályból fogja lekérni az értelmező.

abstract class Singleton
{
	static protected $map=array();
	final static public function instance()
	{
		if (func_num_args())
		{
			throw new Exception('Singleton contructors cannot have arguments.');
		}
		$class=get_called_class();
		if (!isset(self::$map[$class]))
		{
			self::$map[$class]=new $class();
		}
		return self::$map[$class];
	}
	protected function __construct()
	{}
	final protected function __clone()
	{}
}

class A extends Singleton
{}

class B extends Singleton
{}

class C extends A
{}

var_dump(A::instance());
var_dump(B::instance());
var_dump(C::instance());

Akkor sincs nagy gond, ha a PHP fejlesztői megoldják a statikus öröklődést. Annyi történik majd, hogy minden leszármazott osztály kap egy saját tömböt, amiben csak a saját példánya lesz benne.

 
1

na most vagy keso van vagy

Tyrael · 2010. Júl. 27. (K), 23.41
na most vagy keso van vagy mar en nem latok ki a fejembol, de minek egy singleton-hoz reflection.
egyreszt gany, masreszt lassu, miert nem jo a new self? vagy ha leszarmaztatast is akarsz, akkor http://hu.php.net/manual/en/function.get-called-class.php persze ehhez php 5.3 kell a late static binding miatt.

ez megoldas a masodik bekezdesedben felhozott problemakra is, ha a leszarmaztatott osztaly statikus fuggvenyebol el akarod erni a statikus valtozoit, akkor a self helyett a static-ot kell hasznalni (static::$foo) es maris futasidoben lesz feloldva a hivatkozas.
ez a late static binding.

de most latom hogy az uccso kodreszletedben hasznalod is a get_called_class-t.
akkor csak tisztaban vagy vele, hogy mi is ez.

na mind1, mar faradt vagyok agyalni, ird le hogy mit szeretnel/mi a problemad, es akkor vagy tudok segiteni, vagy megvilagosodom.

Tyrael
2

meg lefekves elott

Tyrael · 2010. Júl. 28. (Sze), 07.17
meg lefekves elott hegesztettem kicsit.

<?php

abstract class Singleton{

	protected static $instance;
	
	protected function __clone(){}

	public static function getInstance(){
		if(!isset(static::$instance)){
			$class = get_called_class();
			$args = func_get_args();
			static::$instance = unserialize('O:'.strlen(get_called_class()).':"'.get_called_class().'":0:{}');
			call_user_func_array(array(static::$instance, '__construct'), $args);
		}
		return static::$instance;
	}

}

class MySingleton extends Singleton{

	private $foo;
	private $bar;

	protected function __construct($foo, $bar){
		$this->foo = $foo;
		$this->bar = $bar;
	}

}
$mySingleton = MySingleton::getInstance(123, 4);
var_dump($mySingleton);

unserialize-es trukk csak akkor kell, ha a Singleton leszarmaztatott osztalyaidat mindenkepp a constructorbol szeretned inicializalni, kulonben szebb lenne egy init fuggveny, amibol a vegrehajtas ugy nezne ki, hogy ososztalyban getInstance, az func_get_args+call_user_func_array -jel meghivja felparameterezve a static::init-et, ami egyreszt elvegzi a peldanyositast ($class = get_called_class();new $class;) masreszt inicializalja a getInstance-bol kapott parameterekkel az ujonnan letrehozott peldanyt.

Viszont en amondo vagyok, hogy egyke ne akarjon parametereket kapni, ha erre van szukseg akkor inkabb Factory.

Egyket amugy sem divat manapsag eroltetni, es nem veletlenul.

Tyrael
21

Ja, látom, ügyes a

inf · 2010. Júl. 28. (Sze), 21.38
Ja, látom, ügyes a szerializálós trükk, nem jutott volna eszembe :)
Bizonyos esetekben jól jön az egyke, én leginkább globális változók elkerülésére használom. pl Autoload::instance(), Server::instance() meg hasonlók, ezeken belül ha egy példány kell dolgokból, akkor dekorálok a Factory-n, hogy tárolja le a példányokat egy Map-ben, vagy csak simán setter-ben adom meg, attól függ mennyire általános dologról van szó. Pl a Controller példányoknál Factory kell (mert a kéréstől függ, hogy melyik controller-re van szükség éppen, és azok egymást is hívhatják bizonyos esetekben), de Session-nél meg setter.
23

Bizonyos esetekben jól jön az

Sulik Szabolcs · 2010. Júl. 28. (Sze), 21.53
Bizonyos esetekben jól jön az egyke, én leginkább globális változók elkerülésére használom.

gondoltal mar ra, hogy a singleton is egy globalis dolog? semmi kulonbseg nincs. ha csak erre kell, akkor felejtsd el, hasznalj nyugodtan globalis valtozot.
24

ha csak erre kell, akkor

inf · 2010. Júl. 28. (Sze), 22.10
ha csak erre kell, akkor felejtsd el, hasznalj nyugodtan globalis valtozot

Sokkal több vele a macera, mint a Singleton-nal, meg jobb szeretem az osztályokhoz kötött dolgokat. Létrehozok néhány alap Singleton-t, az összes többi objektumot meg ezeken keresztül érem el.
19

Szia! 5.3.0-val próbáltam,

inf · 2010. Júl. 28. (Sze), 21.31
Szia!
5.3.0-val próbáltam, abban már elvileg van late static binding (legalábbis ezt olvastam php.net-en), viszont nekem a static kulcsszóval ugyanúgy nem volt jó, mint self-el.
A reflection csak a paraméter lista miatt kellett volna, nem feltétlen szükséges, én általában setter-es dependency injectiont használok nem konstruktorosat.
3

mire kell oly sűrűn?

virág · 2010. Júl. 28. (Sze), 08.00
:)
ezt írod:

"Elég sűrűn használom az egyke mintát a most leírt örökléssel."

Majd megöl a kíváncsiság amiatt, hogy megtudjam mire használod sűrűn a singletonokat? Én csak nagyon ritkán látom értelmét és létjogosultságát.
22

Relatív, most éppen egy

inf · 2010. Júl. 28. (Sze), 21.40
Relatív, most éppen egy kisebb frameworkot heggesztek össze, aztán az alapjaihoz kellett párszor, a későbbiekben már nem fog ennyire sűrűn kelleni.
4

Más megközelítés

gphilip · 2010. Júl. 28. (Sze), 12.35
Ittegy érdekes megközelítése a Singletonnak (könyörgöm, ne hívjuk már egykének!)

Singleton (and multiton) with a different approach

Mellesleg nagyon hasznos design pattern (főleg a multiton változat) pl erőforrások kezelésére.
5

kb 15-20 evvel ezelott

Sulik Szabolcs · 2010. Júl. 28. (Sze), 12.36
kb 15-20 evvel ezelott elkezdtek gyujteni a mintakat. errol szol a GoF konyv. azota azert eltelt nehany ev, es osszegyult nemi tapasztalat (es nehany tovabbi minta is).

vannak mintak amelyek ma mar erossen ellenjavaltak, pl a singleton. probalj meg tesztet irni ahhoz a kodhoz, amelyik singletont hasznal. good luck.
6

Igen?

gphilip · 2010. Júl. 28. (Sze), 13.33
A legnépszerűbb kurrens PHP keretrendszerek erősen használják a Singletont (ZF, Symphony).

Nap mint nap írok teszteket Singleton osztályokhoz, erősen TDD orientált munkahelyen dolgozom. Semmi komoly problémám nem akadt ezzel.

Ki tudnád fejteni, kérlek, hogy miért gondolod, hogy ellenjavallt a Singleton használata és mi okoz nehézséget a tesztelésében?
9

http://sebastian-bergmann.de/

Tyrael · 2010. Júl. 28. (Sze), 14.21
az, hogy az elterjedt frameworkok is hasznaljak, meg nem jelent semmit.

http://framework.zend.com/wiki/display/ZFDEV2/Zend+Framework+2.0+Roadmap
Elimination of most singletons. ZF has often been accused of "singletonitis." While we're not sure if we completely agree, we will note that in most cases, the singletons we have have presented a number of problems and led to difficult test cases. Additionally, in most cases, the singleton is unwarranted. We will be refactoring to eliminate these, including in Zend_Controller_Front. In exceptional cases, we will keep them; these include global operations such as autoloading and database connections.


http://www.symfony-project.org/gentle-introduction/1_4/en/06-Inside-the-Controller-Layer
All these core objects are availables through the sfContext::getInstance() singleton from any part of the code. However, it's a really bad practice because this will create some hard dependencies making your code really hard to test, reuse and maintain. You will learn in this book how to avoid the usage of sfContext::getInstance().


http://fabien.potencier.org/article/12/do-you-need-a-dependency-injection-container

A symfony2 el is ment a DI iranyba a korabbi minden singleton felallasbol.

http://sebastian-bergmann.de/archives/882-Testing-Code-That-Uses-Singletons.html
Why is it hard to test code that uses singletons?
Lets have a look at the default implementation of the Singleton design pattern in PHP:

<?php
class Singleton
{
    private static $uniqueInstance = NULL;
 
    protected function __construct() {}
    private final function __clone() {}
 
    public static function getInstance()
    {
        if (self::$uniqueInstance === NULL) {
            self::$uniqueInstance = new Singleton;
        }
 
        return self::$uniqueInstance;
    }
}
?>
The code above declares a class that cannot be instantiated (or cloned) by a client using the new (or clone) operator(s). To get a reference to the only instance of the class one has to use the static method getInstance(). Usually the code that uses the Singleton (which we will refer to as client) is strongly coupled to the getInstance() method:

<?php
class Client
{
    public function doSomething()
    {
        $singleton = Singleton::getInstance();
 
        // ...
    }
}
?>
It is impossible to write a test for the doSomething() method without also invoking the singleton's getInstance() method. This means that we cannot get a fresh instance of the Singleton class and thus have no guarantee that there are no side effects in multiple tests that interact with the singleton.


Tyrael
16

DI

gphilip · 2010. Júl. 28. (Sze), 17.22
Személyes véleményem a dependency injection-ről, hogy óriási bullshit. Mármint maga a buzzword. Amit takar, azt pedig ismerjük és használjuk (ha használjuk) egy ideje.

Mellesleg a dependency injection (ha tényleg így akarunk hívni néhány jól bevált best practice-t) abszolúte nem összeegyeztethetetlen a tágabb értemeben vett singletonnal (ld. a cikk, amit az első bejegyzésemben írtam, 5 perc alatt átalkítható "containerré" vagy inkább lookup osztállyá).
17

furcsa nekem a

Tyrael · 2010. Júl. 28. (Sze), 19.31
furcsa nekem a hozzaallasod.
A patternek tobbnyire best-practice-ek, amik egy egy problemara kielegitonel jobb megoldast kinalnak.
Es ezeknek hol jobb hol roszabb neveket adnak/adunk amiatt, hogy lehessen rola hoszabb magyarazkodas nelkul beszelni.
A DI az egy ugyanolyan pattern, mint a tobbi, talan egy picit jobb.
http://martinfowler.com/articles/injection.html
nincs benne semmi egetrengeto, nem is ujdonsag.
igazabol talan ugy fogalmaznek, hogy bizonyos korokben most kezdik ujrafelfedezni ezt az eszkozt.

Az hogy a tagabb ertelemben vett singletonnal mennyire osszeegyeztethetetlen, az attol fugg, hogy mit nevezel tagabb ertelemnek, es osszeegyeztethetetlennek. :)

A cikket elolvastam, itt a velemenyem rola:
Multiton = Registry + Singletons
A srac megoldasa:
Factory+Multiton

ezekkel onmagukban nincs baj, de semmivel nem lett csokkentve a statikus kulso dependencia azzal, hogy a singletonjaidat sokkal okosabb Multiton-okra cserelted.

Ha a peldanyaidat injectalod a fugvenyeidbe ahelyett, hogy ok nyulkalnanak ki es szednek ossze a fuggosegeidet, akkor hasznalhatsz nyugodtan Singletont.

Szoval nem a Singletonnal van a problema, hanem azzal, ahogyan felallitod, es biztositod a fuggosegeket a fuggvenyeid/osztalyaid kozott.

Tyrael
18

Igaz

gphilip · 2010. Júl. 28. (Sze), 19.59
Teljesen egyetértek az utolsó bekezdéseiddel.

Nekem mindössze azzal van problémám, hoyg a DI nem egy újdonság, hanem inkább egy programozási gyakorlat. Szerintem semmi köze nincs a design patternekhez, amik azért ennél jóval konkrétabb dolgokat írnak le. Ezt az is bizonyítja, hogy a DI-t számos különböző - ha úgy tetszik - design patternnel megvalósíthatod.

Szűk értemeben vett singleton alatt a "klasszikus" (getInstance) singletont értem, ami eleve egy kicsit sántít, hiszen egy oszálynak függetlennek kell lennie attól, hogy hogyan és mennyi objektumot példányosítok belőle. Tágabb értelemben véve a Singleton az, amikor egy osztályból egy objektumpéldányt hozunk létre és kizárólag ezt használjuk (már-már statikusan).

Összeegyeztethetelennek azt nevezem, ha ezt írod:
A symfony2 el is ment a DI iranyba a korabbi minden singleton felallasbol.


Miközben ez nem két ellentétes irány.
20

szvsz csoppet felreertik itt

Sulik Szabolcs · 2010. Júl. 28. (Sze), 21.34
szvsz csoppet felreertik itt az emberek egymast.

valaminek menedzselni kell az egyetlen peldanyt, ami biztos, hogy nem maga az osztaly kene, hogy legyen. ez lenne az a reteg, amit korabban irtam. emellett el kellene felejteni a new operator hasznalatat ezen a retegen kivul (newable objektumok kivetelevel). kis segitseg a megerteshez.

ez az egyik resze. a masik resze pedig maga a peldakodokbol lathato. az a baj a singleton mintaval, mint olyannal, hogy ezt az alabbi modon hasznaljak (azzal a cellal hozzak letre, hogy igy hasznaljak), es ez meglehetosen nehezen tesztelheto:

class Client  
{  
    public function doSomething()  
    {  
        $singleton = Singleton::getInstance();  
   
        // ...  
    }  
}

$client = new Client();
$client->doSomething();
ezzel szembe ez a megoldas mar rendben van, siman tesztelheto:

class Client  
{
    /**
     * @param Singleton $singleton
     */
    public function doSomething($singleton)
    {
        // ...  
    }  
}

$singleton = Singleton::getInstance();
$client = new Client();
$client->doSomething($singleton);
amire oda kell figyelni, hogy az utolso 3 sor megfelelo helyre keruljon.

UI: ez a singleton minta, lehet rajta csavargatni, atnevezgetni, es arrol szol, hogy sajat maga menedzseli az egyetlen peldanyat (privat konstruktor, clone, statikus metoduson keresztul peldanyosithato).
8

ZF "menekül"

erenon · 2010. Júl. 28. (Sze), 14.20
A ZF 2.0 jelenlegi draftjaiban ahol tudják, kiírtják a Singleton mintákat. Mert nem feltétlen szükségesek, mert nincs igazán értelmük, vagy mert nehéz tesztelni őket (megjegyzem; ez nem kéne, hogy érv legyen, meg kell oldani a tesztelést és kész).
10

ez nem kéne, hogy érv legyen,

Tyrael · 2010. Júl. 28. (Sze), 14.23
ez nem kéne, hogy érv legyen, meg kell oldani a tesztelést és kész


”The secret in testing is in writing testable code” Miško Hevery

Tyrael
11

Tyraelnel a pont :) annyit

Sulik Szabolcs · 2010. Júl. 28. (Sze), 14.36
Tyraelnel a pont :)

annyit tennek meg hozza, hogy alapvetoen hibas az az elkepzeles, hogy egy osztaly feladata "csinalni" valamit, es meg onmaga felugyeli azt, hogy egy peldany legyen belole. ez erosen SRP violation.

a singleton egy letrehozasi minta. egy idealis vilagban (ugye arra tartunk :) ) van egy reteged az alkalmazasodban, amely felelos az objektum graf letrehozasaert. egy ilyen reteg felelossege lehet az, hogy egy adott objektum csak egy peldanyban letezhet. az o felelossege, hogy az egyetlen peldanyt injektalja mindenkinek, akinek szuksege van ra. igy a unit tesztek utjaban sem all senki.

mas oldalrol, hogyan tesztelsz egy ilyen kodot, mikor nem tudod mockolni a Db peldanyt?

class Foo
{
  function bar()
  {
    $db = Db::getInstance();
    //....
    if (!$db->insert($query, $params)) {
      throw new DbException();
    }
  }
}
UI: tudom, tudom, lehet spec settereket hozzaadni a singleton-hoz - setTestInstance() pl - de ez meg csak nagyon legacy kod eseten javalott eljaras, es szigoruan ideiglenes, amig ki nem dobhato a singleton

es meg nehany link:
- Singletons are Pathological Liars
- Flaw: Brittle Global State & Singletons
12

Lehet, hogy rosszul látom, de

Török Gábor · 2010. Júl. 28. (Sze), 15.07
Lehet, hogy rosszul látom, de ez nem kizárólagosan a singleton minta hibája. Mennyivel tudod jobban tesztelni a kódot a következő esetben? A függőség ugyanúgy fennáll:

function bar()
{
    $db = new Db();
    // ...
}
Illetőleg DI mellett is csinálhatsz olyat, hogy argumentként érkezik a $db, amit a hívó környezetben Db::getInstance()-szal adsz meg.
13

A lenyeg elsikkadt. Nem a

Tyrael · 2010. Júl. 28. (Sze), 15.17
A lenyeg elsikkadt.
Nem a singleton az egyetlen olyan pattern/eszkoz amivel meg tudod neheziteni a tesztelest, de most errol volt szo.
A legtisztabb es legjobban tesztelheto eset az az, hogy a kod egyetlen dependenciaja input szempontbol a kapott argumentumok, es idealis esetben, modositast csak a kapott parametereken vegez.
Ezaltal jol mockolhatova valik a mukodese.
Persze a valo vilag nem mindig ilyen idealis, ilyenkor jonnek az egyeb trukkok, de ez mar nem olyan kenyelmes tesztelesi szempontbol, mint az idealis eset.

A DI-os felvetesed szinten ebbe a kategoriaba esik. Ha valamely fuggvenyedbe ilyen mesterseges fuggosegeket teszel, mint peldaul direkt fajlmuvelet wrapper fuggveny/osztaly nelkul, direkt db muvelet, globalis/statikus valtozok/fuggvenyek/osztalyok piszkalasa, akkor ott szinten nehezebb a megfelelo teszteles.

Persze minel tobbet hasznalod, a DI-t, annal kevesebb es valoszinuleg magasabb szinten definialod ezeket az eroforrasokat, ezaltal kevesebb helyen kell, es sokkal konyebb lesz mockolni oket.

Tyrael
14

Megint Tyraelnel a pont.a

Sulik Szabolcs · 2010. Júl. 28. (Sze), 15.39
Megint Tyraelnel a pont.

a problema, hogy global state cuccost hasznalsz a kodban (az osztaly phpban globalis dolog), ami valojaban a kod fuggosege. injektald be a fuggosegeket. errol szol az egesz. nem tunik neheznek az egesz. kerdes miert csinaljak megis rosszul az emberek? szemleletvaltasrol is szol a dolog.
15

Ezt érdemes elolvasni a témában

Thoer · 2010. Júl. 28. (Sze), 15.43
Misko a Googlenél tanítja a zseniket jól tesztelhető kódot írni.
http://misko.hevery.com/code-reviewers-guide/
7

Csatlakozom

Török Gábor · 2010. Júl. 28. (Sze), 13.45
25

egyéb

mrbig · 2010. Júl. 29. (Cs), 14.23
Nekem itt más problémáim is vannak. Miért kell egy singletont paraméterezni? A következő getInstance() hívás mit fog csinálni, ha az előzőektől eltérő paramétert kap? Ez kissé borítja a Singleton patternt.

A másik dolog: miért kell Singleton ősosztályt gyártani? Egy meglehetősen egyszerű design patternről van szó, amit egyszerű implementálni bármely osztályban. Singletonokat ritkán örököltetünk (mivel ritkán is használjuk őket ;) így a rengeteg kód, amit az örököltetés megkerülésére írtál általában felesleges. És mivel nincs többszörös öröklődésünk, ezért elég pazarlásnak érzem azt, hogy az ősosztály a design patternt határozza meg, nem pedig a szemantikai őst.
26

Hmm, egyszer használtam már

inf · 2010. Júl. 29. (Cs), 22.36
Hmm, egyszer használtam már többszörös öröklésre, egyébként meg nem érzem problémának, amit írsz, egyelőre még nem fordult elő velem, hogy ütközött volna más őssel, talán pont a ritka használat miatt. Egyébként feljebb már írtam, hogy az ilyen esetek elkerülésére csináltam olyan factory-t, ami a megadott osztályokat csak egyszer példányosítja, utána pedig a példánnyal tér vissza mindig. Éppen ezt fejlesztem tovább hasonlóra, mint a multiton, amit belinkeltek, nem egy nagy kunszt, bár kellenek bizonyos megszorítások hozzá.
27

Vélemény

whiteman0524 · 2010. Júl. 30. (P), 12.44
Ha egy statikus függvényt a szülőből örököl egy osztály, akkor abban a statikus változók a szülő statikus változóira mutatnak. A PHP fejlesztői szerint ez teljesen rendben van, szerintem nem.


Én a kedves PHP fejlesztőkkel értek egyet, ugyanis egy statikus változó célja, hogy az adott változó mindig ugyan arra a címre mutasson. Mivel egy statikus változó mindig egy helyre mutat, ezáltal a függvény ami őt felhasználja is csak ugyan azzal a címmel babrálhat. Öröklődésnél ez meg pláne értelmet kell hogy nyerjen, mivelhogy egy származtatott osztály lényegében egy ős osztály módosítva és/vagy kibővítve. Így tehát, ha egy származtatott osztály megörökli egy statikus változó "használati jogát", akkor ő is ugyan azt a címet kell hogy elérje, mint a szülő.

Emlékezzünk vissza OO tanulmányaink kezdetére. A statikus változó célja, hogy osztályonként csupán egy legyen belőle. Egy származtatott osztály nem egy új osztály, hanem egy módosított ős osztály, eképpen értelmet nyer az "osztályonként csupán egy" kifejezés. Ha Minden származtatott osztályban más és más címre mutatnának ugyanazon nevű statikus változók, akkor nem öröklődésről beszélnénk, mivel nem "örökölnék" a címet :)

Szóval ezzel nem kell vitába szállni, és nem kell lenyelni hogy "ez van ezt kell szeretni" :) Ez logikailag így helyes és a kedves fejlesztők nagyon is értik a dolgukat :)
28

Én nem tudom, hogy ez e a

inf · 2010. Júl. 30. (P), 16.26
Én nem tudom, hogy ez e a szokásos más nyelvekben is, ha igen, akkor legyen. :-) Én más logika szerint gondoltam, de így is megírható vele az ősosztály, amire szükségem volt. kopp-kopp
29

ettol fuggetlenul ahogy irtam

Tyrael · 2010. Júl. 31. (Szo), 18.05
ettol fuggetlenul ahogy irtam a self::$foo helyett static::$foo -val lehet hivatkozni a leszarmaztatott osztaly statikus valtozojara.
ugyanez persze mukodik metodusokra is.

Tyrael
30

Ha ezt vesszük, akkor

inf · 2010. Júl. 31. (Szo), 21.30
Ha ezt vesszük, akkor szerintetek nem probléma, hogy nem következetes az osztályváltozók öröklése? Self-el az ős osztályváltozóját lehet elérni, static-al pedig a leszármazottét...
Én elfogadom, ha úgy gondolják, hogy az öröklött változó az ős-höz tartozik, de akkor tényleg tartozzon oda. Szerintem van egy kis zavar a fejlesztők fejében, hogy mit is akarnak.
31

szerintem kovetkezetes,

Tyrael · 2010. Aug. 1. (V), 10.40
szerintem kovetkezetes, raadasul nagyon hasznos.
late static binding nelkul egy csomo dolgot eddig csak nagyon korulmenyesen lehetett megcsinalni.
igazabol csak annyi problemam van vele, hogy ez johetett volna mar az 5-os php-val.

Tyrael
32

Értem, de ha az a jobb, akkor

inf · 2010. Aug. 1. (V), 10.51
Értem, de ha az a jobb, akkor miért hagyták meg a régit?
33

valószínűleg ugyan azért,

winston · 2010. Aug. 1. (V), 11.00
valószínűleg ugyan azért, amiért a sok régi, adott esetben az újakhoz képest teljesen más konvenciót követő, vagy feleslegessé vált függvényeket is bennehagyták: kompatibilitás. senki nem szeretné, ha upgradeli a php-t az alkalmazása alatt, és az azon nyomban összedőlne. php-ék, legyen bár sok érdekes döntésük a fejlesztések során, de a kompatibilitásra mindig ügyelnek.
34

parseolas kozbensokkal

Tyrael · 2010. Aug. 1. (V), 12.35
parseolas kozbensokkal egyszerubb/gyorsabb feloldani az ilyen referenciakat, ergo ha lecsereltek volna a regi mukodest az ujra, akkor amellett, hogy egy csomo alkalmazas eltorne, ami epitett a regi viselkedesre, meg teljesitmeny szempontbol is problemas lenne.
ertsd aki nem szarmaztat osztalyokat, vagy szarmaztat, de a szarmasztatott osztalybol nem akar statikus methodust hivni, ott is atkerulne a self feloldasa forditasi idobol futasi idobe.

Tyrael