> -----Original Message----- > From: Daniel Kolbo [mailto:kolb0057@xxxxxxx] > Sent: 11 July 2010 23:19 > > Hello PHPers, > > I'm having some trouble understanding some PHP behaviour. The > following > example script exhibits the behaviour which I cannot understand. I'm pretty sure that this is *not* a bug. I'll answer your last question first, and then demonstrate with your code. > I'm nervous to use "self::$a = $this;" because I don't want to be > copying the whole object. However, isn't $this just a reference to > the > object, so "self::$a = $this;" is just copying the reference and not > the > actual object, right? Not exactly, although everybody seems to refer to it as a reference for convenience. Most of the time it doesn't matter, but when you start introducing references to objects it can - it's better to think of an object variable as holding the object's *handle* (see http://php.net/anguage.oop5.references.php for more on this), so it's clear exactly what a reference is referencing. Now for your code: > [code] > <?php > > class A > { > public static $a = 3; > > function __construct() > { > //self::$a = $this; //[i] > self::$a =& $this; //[ii] > } > } > > class B extends A > { > function __construct() > { > parent::__construct(); > } > } > > class C { > var $c; > > function __construct() > { > $this->c =& A::$a; > } > > } > > > $c = new C; [i] & [ii] in C::__construct(): $c->c = reference to same value as A::$a (currently (int)3) NOTE: because of how references work, A::$a is now also a reference to (int)3. > $b = new B; [i] in A::__construct(): A::$a = handle of object B(1) (also assigned to global $b) NOTE: $c->c, as reference to $A::a, now also references handle of object B(1) [ii] in A::__construct(): A::$a = reference to handle of object B(1) NOTE: since we are assigning a new reference to a variable which is already a reference, ONLY this reference changes -- so $c->c is still a reference to (int)3...! > $cee = new C; Irrelevant -- the damage has already been done! > var_dump($c->c); // [i] prints object(B), but [ii] prints int 3 > var_dump($cee->c); // [i] prints object(B), and [ii] prints > object(B) ... which is correct according to my interpretation. This has been such a regular confusion, that some time ago I wrote this test script: <?php class test { public $me; } $t = new test; $t->me = 'Original'; $copy_t = $t; $ref_t = &$t; $copy_t = new test; $copy_t->me = 'Altered Copy'; echo <<<RESULT1 Original: $t->me<br /> Copy: $copy_t->me<br /> Reference: $ref_t->me<br /> RESULT1; $ref_t = new test; $ref_t->me = 'Altered Reference'; echo <<<RESULT2 <br /> Original: $t->me<br /> Copy: $copy_t->me<br /> Reference: $ref_t->me<br /> RESULT2; $s = 'String'; $copy_s = $s; $ref_s = &$s; $copy_s = 'String Copy'; echo <<<RESULT3 <br /> Original: $s<br /> Copy: $copy_s<br /> Reference: $ref_s<br /> RESULT3; $ref_s = 'String Reference'; echo <<<RESULT4 <br /> Original: $s<br /> Copy: $copy_s<br /> Reference: $ref_s<br /> RESULT4; ?> Which gives this output: Original: Original Copy: Altered Copy Reference: Original Original: Altered Reference Copy: Altered Copy Reference: Altered Reference Original: String Copy: String Copy Reference: String Original: String Reference Copy: String Copy Reference: String Reference Which demonstrates how exactly the behaviour of objects correlates to scalars with regards to copying and referencing -- but may not be exactly what you expect if you think of object variables as always holding a reference to the object. I would heartily recommend always to think of an object variable as holding the object's *handle*, and *not* a reference - this may croggle your brain a bit, but makes it a Lot clearer what's happening in edge cases like this. Cheers! Mike -- Mike Ford, Electronic Information Developer, Libraries and Learning Innovation, Leeds Metropolitan University, C507, Civic Quarter Campus, Woodhouse Lane, LEEDS, LS1 3HE, United Kingdom Email: m.ford@xxxxxxxxxxxxxx Tel: +44 113 812 4730 To view the terms under which this email is distributed, please go to http://disclaimer.leedsmet.ac.uk/email.htm -- PHP General Mailing List (http://www.php.net/) To unsubscribe, visit: http://www.php.net/unsub.php