Порядок уничтожения объектов гарбедж коллектором в PHP5 по окончанию работы скрипта.

Anton

Just Programmer
Порядок уничтожения объектов гарбедж коллектором в PHP5 по окончанию работы скрипта.

Собственно сабж.

Есть ли какой-то алгаритм который определяет в каком порядке будут уничтожаться объекты гарбедж коллектором по окнчанию работы скрипта?

Я сделал несколько тестовых скриптов. По результатам их работы я сделал вывод, что объекты будут уничтожаться в порядке обратном их созданию ... но когда стал работать с реальным кодом, порядок оказался другой. :-(

Никто неможет ничего подсказать на этому поводу?
 

IntenT

SkyDiver
Anton
Ты объяснить можешь, зачем тебе все это надо?
(и про остальные 2 темы тоже)
 

Фанат

oncle terrible
Команда форума
Кстати, да.
Если ты так глубоко копаешь - почему бы тебе не посмотреть в исходниках?
 

Anton

Just Programmer
Да тут все просто по этой теме.

Есть классы сущностей.

В деструкторе сущности, если было что-то изменено в сущносте происхоит обнавление сведений в БД.

Завершением транзакции завдует деструктор отдельного объекта, он собственно и решает надо делать в конце COMMIT или ROLLBACK. Соответственно необходимо, что бы это был подчищен коллектором после классов сущностей.

Естественно есть еще много способов решения данной проблемы с помщью других методик, но проще всего она бы решилась именно таким способом.

-~{}~ 11.03.05 11:41:

Пржде чем лезть в исходники лучше поспрашать ... :)) Вдруг кто уже капашился. А то я там могу долго ползать и материться :)

-~{}~ 11.03.05 11:41:

А какой код-то в студию??
 

su1d

Старожил PHPClubа
кажется РНР официально не даёт никаких гарантий на порядок вызова деструкторов, так что на "грамотное" (в смысле желаемое) уничтожение всех объектов рассчитывать не приходится.
 

Anton

Just Programmer
У меня складываеться такое же впечатление.

Просто у них еще и порядок при одной и той же ситуации может изеняться сбора мусора, что совсем подозрительно.
 

Screjet

Новичок
Нету как такового "сбора мусора". Есть освобождение памяти.
Порядок в деструкторах есть. Они вызываются в последовательности создания объектов. Пример:
PHP:
class test {
  function __construct($name){
    $this->name = $name;
  }
  function __destruct(){
    echo "Desctructor in {$this->name}\n";
  }
}
$glob_var0 = new test("first #0");
$glob_var1 = new test("first #1");
function glob_func(){
  $var = new test("second");
}
// деструктор "second", по завершению ф-ции переменные освобождаются
glob_func();
// деструктор "first #0" (по событию освобождения памяти переменные освобождаются)
// деструктор "first #1" (..)
 

Anton

Just Programmer
Ага ... а вот от этого уже можно поплесать и подумать как бы реализоваться.

Спасибо большое Screjet. Именно что-то такое я и хотел услышать. Спасибо :))
 

tony2001

TeaM PHPClub
>кажется РНР официально не даёт никаких гарантий на порядок вызова деструкторов
FIFO
 

Blindman

Новичок
> FIFO

Тоже не гарантировано

PHP:
<?php
    class Test
    {
        private static $count = 0;
        private $serial;

        public function __construct()
        {
            $this->serial = ++self::$count;
            echo "Constructing instance #{$this->serial}\n";
        }

        public function __destruct()
        {
            echo "Destructing instance #{$this->serial}\n";
        }
    }


    $a = array();
    $a[] = new Test;
    $a[] = new Test;
    $a[] = new Test;
    $a[1] = new Test;
    $a[] = new Test;
Код:
Constructing instance #1
Constructing instance #2
Constructing instance #3
Constructing instance #4
Destructing instance #2
Constructing instance #5
Destructing instance #1
Destructing instance #5
Destructing instance #3
Destructing instance #4
 

Anton

Just Programmer
То что не FIFO стопудово ... проверял еще до того как писать.
 

Blindman

Новичок
Blindman, ты же этим насильно убиваешь instance #2.
это очевидно.
вот и получаешь то, что видишь
в остальном, как видишь, чистый FIFO.
Не вижу. Смотри внимательнее

Destructing instance #1
Destructing instance #5
Destructing instance #3
Destructing instance #4
 

Blindman

Новичок
> var_dump($a) сделай в конце и посмотри на object(Test)#<idx>.

Посмотрел. Элементы хранилища объектов используются повторно, и предсказать порядок вызова деструкторов невозможно
 

Screjet

Новичок
Blindman
Есть смысл почитать ман на предмет деструкторов.
Тони ясно объяснил где ты прибиваешь объект (+destructor) и создаешь новый (уже с деструктором #5).
 

Blindman

Новичок
Screjet
Где прибивается объект и создается новый (кстати, #4), мне объяснять не надо.
А ты сможешь объяснить, почему сначала вызывается деструктор объекта, созданного первым, затем деструктор последнего объекта, и лишь затем все остальные?
 

svetasmirnova

маленький монстрик
Blindman
>А ты сможешь объяснить, почему сначала вызывается деструктор объекта, созданного первым, затем деструктор последнего объекта, и лишь затем все остальные?

В терминах запуталась, но вроде из-за того, что их адреса идут именно в этом порядке.
 

su1d

Старожил PHPClubа
вот, кажется нашёл свой источник (хотя, пост старый):
Andi Gutmans wrote:
A *VERY* important implication is that you cannot, and must not
rely in any way on the order of destruction during shutdown. It runs in
no particular order. That means that by the time the destructor for
your object $foo is called, a reference to some other object $bar may
already be post-destruction. Note that it will still be 'intact' and
accessible in the sense that if you access it - there won't be crashes.
However, if this object does indeed have a destructor, it can be
considered semantically wrong to touch this object at this point.
 
Сверху