(17-06-2009, 10:26 AM)Ter Rowan a écrit : $this->_byType = $this->_byBagEn PHP5, quand la partie droite de l'affectation est un objet, c'est strictement équivalent (affectation par référence automatique).
et pas
$this->_byType = &$this->_byBag
PHP ne videra jamais la mémoire tant qu'il reste une référence à un objet, quand bien même elle ne devrait plus être active.
Exemple classique des références croisées :
Code PHP :
<?php
class Inventaire {
protected $proprietaire;
public function __construct(Personnage $proprietaire) {
$this->proprietaire = $proprietaire;
}
}
class Personnage {
protected $inventaire;
public function __construct() {
$this->inventaire = new Inventaire($this);
}
}
// Cet objet ne sera jamais retiré de la mémoire
$perso = new Personnage();
unset($perso); // $perso->inventaire étant une référence vers $perso, la mémoire n'est pas récupéré.
Triste, mais inévitable. La bonne nouvelle étant que la mémoire est bien récupérée au niveau du système après l'exécution du script, encore heureux
Note : c'est encore plus flagrant si on rajoute un destructeur dans la classe Personnage ou Inventaire (avec dedans un bête echo "quelque chose"), on se rend compte que ce destructeur n'est *jamais* appelé.
Le seul moyen est d'écrire un destructeur et qu'on l'appelle manuellement. Le code suivant ne provoquera pas de fatal error :
Code PHP :
<?php
...
class Personnage {
...
public function __destruct() {
unset($this->inventaire);
}
...
while (true) {
$perso = new Personnage();
// unset($perso); // ne fait rien : le destructeur n'est pas appelé car il reste une référence
$perso->__destruct(); // appel forcé au destructeur, cette fois ça marche car la référence qui restait est supprimée.
}