# Pre-Destructor magic function?

- Thread: https://externals.io/message/31531
- Original archive: https://news-web.php.net/php.internals/31531
- Started by Nathanael D. Noblet on 2007-08-10T23:01:17+00:00
- Messages: 5
- Reply by email to internals@lists.php.net
- More for agents: search with https://externals.io/search.md?q={query} · JSON API at https://externals.io/api · documentation at https://externals.io/llms.txt

---

## #31531 — Nathanael D. Noblet — 2007-08-10T23:01:17+00:00

URL: https://externals.io/message/31531#31531

Hello,
   I have a case where an object has a few variables, a couple of which 
are objects which hold references back to this object.

So very simply something like

class A {
   var B
}

class B {
   var A
}

When doing something like so

$obj = new A(); in a loop the object's never released from memory 
because of the internal references it holds. __destruct is not called 
until the end of script execution etc. Now normally in a web request 
situation this isn't a big deal. However I'm using it in a batch and 
loop over 22 000 records. Since re-assigning the single object I use 
isn't freeing any memory it consumes quite a bit. I have gotten around 
it by creating a special function in the object to manually release the 
recursive references. However it would be nice if there were some sort 
of 'magic' function that could be called on an object so that it knows 
it is being deleted, sort of like a __preDestruct or something like 
that... Is that a bad idea? Or I guess better able to handle recursive 
references in objects would be the other way to solve it I guess.

Any feedback is welcome.

-- 
Nathanael D. Noblet

---

## #31533 — Arnold Daniels — 2007-08-11T06:28:53+00:00

URL: https://externals.io/message/31531#31533 · In reply to: #31531

Hi Nathanael,

If you've been watching the list you could have seen that David Wang 
(god bless his soul) is working on this at the moment. Have a look at 
http://marc.info/?l=php-dev&m=118418663902191&w=2.

You'll have to stick with your custom solution for now though.

Best regards,
Arnold


Nathanael D. Noblet wrote:
> Hello,
>   I have a case where an object has a few variables, a couple of which 
> are objects which hold references back to this object.
>
> So very simply something like
>
> class A {
>   var B
> }
>
> class B {
>   var A
> }
>
> When doing something like so
>
> $obj = new A(); in a loop the object's never released from memory 
> because of the internal references it holds. __destruct is not called 
> until the end of script execution etc. Now normally in a web request 
> situation this isn't a big deal. However I'm using it in a batch and 
> loop over 22 000 records. Since re-assigning the single object I use 
> isn't freeing any memory it consumes quite a bit. I have gotten around 
> it by creating a special function in the object to manually release 
> the recursive references. However it would be nice if there were some 
> sort of 'magic' function that could be called on an object so that it 
> knows it is being deleted, sort of like a __preDestruct or something 
> like that... Is that a bad idea? Or I guess better able to handle 
> recursive references in objects would be the other way to solve it I 
> guess.
>
> Any feedback is welcome.

---

## #31536 — Nathanael D. Noblet — 2007-08-11T17:34:29+00:00

URL: https://externals.io/message/31531#31536 · In reply to: #31533

Arnold Daniels wrote:
> Hi Nathanael,
> 
> If you've been watching the list you could have seen that David Wang 
> (god bless his soul) is working on this at the moment. Have a look at 
> http://marc.info/?l=php-dev&m=118418663902191&w=2.


Wonderful! I just joined a few moments before so hadn't seen any traffic 
  on this list. I guess I should start testing out his changes.

Thanks,
-- 
Nathanael D. Noblet

---

## #31539 — Richard Lynch — 2007-08-12T05:42:37+00:00

URL: https://externals.io/message/31531#31539 · In reply to: #31531

I'm not a PHP OOP expert, so this could be 100% wrong, but...

> $obj = new A(); in a loop the object's never released from memory
> because of the internal references it holds. __destruct is not called
> until the end of script execution etc. Now normally in a web request

If __destruct isn't being called until the end of the script, then PHP
thinks you still have some way of accessing that object, and it can't
free it.

> situation this isn't a big deal. However I'm using it in a batch and
> loop over 22 000 records. Since re-assigning the single object I use
> isn't freeing any memory it consumes quite a bit.

Perhaps set some things to `NULL` or unset them explicitly to convince
PHP that you are done with them.

> I have gotten around
> it by creating a special function in the object to manually release
> the
> recursive references.

Well, there you go.

Release the references so PHP knows you are done with them.

> However it would be nice if there were some sort
> of 'magic' function that could be called on an object so that it knows
> it is being deleted, sort of like a __preDestruct or something like
> that... Is that a bad idea? Or I guess better able to handle recursive
> references in objects would be the other way to solve it I guess.

__destruct is called right before PHP destroys the object.

There really isn't any event of any significance for a __perDesctruct...

Either you're done with it, or you're not...

-- 
Some people have a "gift" link here.
Know what I want?
I want you to buy a CD from some indie artist.
http://cdbaby.com/browse/from/lynch
Yeah, I get a buck. So?

---

## #31540 — Arnold Daniels — 2007-08-12T19:58:04+00:00

URL: https://externals.io/message/31531#31540 · In reply to: #31539

Hi Richard,

class A {
  public $bs = array();
  function addB() {
     $this->bs[] = new B($this);
  }
}

class B {
  public $parent;
  function __construct($parent) {
     $this->parent = $parent;
  }
}

function doSomething() {
  $a = new A();
  $a->addB();
  $a->addB();
}

See the problem? The object $a isn't available from global space, but 
because of the circular reference, A and all its Bs won't be picked up 
by the garbage collector. Have this 22 000 times and you run out of memory.

Best regards,
Arnold



Richard Lynch wrote:
> 
>
> I'm not a PHP OOP expert, so this could be 100% wrong, but...
>
>   
> > […]
>
> If __destruct isn't being called until the end of the script, then PHP
> thinks you still have some way of accessing that object, and it can't
> free it.
>
>   
> > […]
>
> Perhaps set some things to `NULL` or unset them explicitly to convince
> PHP that you are done with them.
>
>   
> > […]
>
> Well, there you go.
>
> Release the references so PHP knows you are done with them.
>
>   
> > […]
>
> __destruct is called right before PHP destroys the object.
>
> There really isn't any event of any significance for a __perDesctruct...
>
> Either you're done with it, or you're not...
