POV-Ray : Newsgroups : povray.off-topic : Programming design question, related to GC : Programming design question, related to GC Server Time
1 Oct 2024 07:22:48 EDT (-0400)
  Programming design question, related to GC  
From: Warp
Date: 11 Apr 2008 14:00:01
Message: <47ffa720@news.povray.org>
Assume we have some kind of class, let's call it Engine, with one unique
instance. We also have an abstract interface, let's call it EventListener,
which contains callback functions.

  Classes can implement the EventListener interface and register themselves
to the Engine object. The latter will call the callback functions of the
registered objects when certain events happen.

  In C++ we could do, for example, so that we create a class, let's call
it ListeningClass, which implements EventListener, and the constructor
of this class registers itself to the Engine object (by giving itself as
a raw pointer to it). The destructor of ListeningClass tells the Engine
object to remove this object from the list of callback objects.

  This is a safe thing to do: Whenever such object is destroyed, it
automatically tells the Engine object to remove that raw pointer from
its internal list of listener objects. Thus the Engine object will never
call a destroyed listener.

  Suppose that we have to instantiate ListeningClass dynamically for
whatever reasons (for example because it has to be shared). We can use
reference counting to handle this: No matter how much the object is
shared and moved around, when the last reference to it is destroyed,
the ListeningClass instance is also destroyed, which then causes it to be
removed from the Engine object. This works because the Engine object only
has a raw pointer to the callback object, not a reference-counted one.
(And, as noted previously, this is completely safe.)

  However, what happens in a GC'd language where you basically *can't*
implement a reference-counted system like this (which is the case eg.
with Java)?

  There's just *no way* for the ListeningClass to automatically tell the
Engine object to remove the reference to it because the former cannot
automatically know when it's not used anymore.

  This will cause the Engine object to hold onto the references to all
listener objects even if all the other references to those objects die.
Thus the object will never by garbage-collected.

  The only solution for this would be for the program to explicitly remove
listening objects from the Engine object when they are not used anymore.
However, this is error-prone, as we all know: Whenever you have to free
some resource manually there's a big chance that in some situations it
will never happen.
  If this is so, then what we have is a memory leak. In a GC'd system.

  Any ideas about how this sould be done instead?

-- 
                                                          - Warp


Post a reply to this message

Copyright 2003-2023 Persistence of Vision Raytracer Pty. Ltd.