Navigation:  Programming Cookbook >

Weak References and Finalization

Previous pageReturn to chapter overviewNext page

A particularly useful feature of Smalltalk is automatic garbage collection. The beauty of garbage collection is that it relieves one of the responsibility of explicitly managing the lifetime of objects, and consequently one doesn't have to spend 80% of one's time fixing bugs caused by holding onto memory for too long or short a time. You might be familiar with the nightmares of explicit memory management in other languages! Smalltalk's philosophy, in contrast, is that memory management is the responsibility of the environment, not the programmer, and so the Virtual Machine (VM) automatically reclaims the space used by objects when they are no longer in use. The VM determines that an object is garbage by detecting that there is no reference path by which it can be reached from the "roots of the world". In Smalltalk the system dictionary (imaginatively named Smalltalk) contains the roots of the world, and every other interesting object is reachable from there. Even if an object references itself, or is part of an incestuous chain of indirect circular references, the VM will find it and reclaim it if it is not reachable from a root.

There is, of course, a fatal flaw in Smalltalk's garbage collection scheme - it is based on the assumption that the entire world is implemented in Smalltalk (a pleasant thought, but not entirely practical).

Early versions of Smalltalk-80 did indeed provide the entire operating system, but today we need to integrate with external systems that provide windowing and other operating system services. In order to do this, we need to be able to "own" external resources (typically by holding onto a "handle"), and to release them when they are no longer required. For example, if we wanted to implement a Bitmap class for Dolphin, then we would need to make use of the native Windows™ bitmaps by encapsulating their handles in a Dolphin class. When the Dolphin Bitmap object is garbage collected we must ensure that the external resource is also freed. We don't want to explicitly program the freeing every time we're finished with a bitmap as we don't always know when we're finished, it's not consistent with other objects, and, in any case, its far too much bother, and far too easy to get wrong. To enjoy those sort of masochistic pleasures we suggest using C++. The solution to the problem in Dolphin is Finalization.

There is a further problem which manifests itself in circumstances where we need to maintain global registries of objects, but only while they remain "live".

As Smalltalk programmers concerned with our personal hygiene, we don't like globals, but there are occasions when we need some means of globally accessing objects. We might, for example, prefer (or need) to share a single instance of a class so that no more than one instance has the same "value" or contents.

Symbols are an example of a class where we need a single unique instance for each representable value, and where we require global access to these instances. There is also an infinite set of possible symbol values, so we cannot simply pre-create all the instances. The solution is to use a global registry of symbols (a symbol table). Each time we come across a symbol value we've not seen before, we put a new symbol into the symbol table so that we can use it again the next time we see that value. This is a great way to acquire a symbol table. It is also a great way to acquire a load of symbols which are no longer used, except in the symbol table (including all the typos one makes when programming). We could periodically purge all the dead symbols, but this requires explicit intervention, and is hardly a satisfactory solution to the problem in general.

So occasionally we need to maintain registries of objects internal to Smalltalk. The Dolphin solution to this problem is Weak References.

We will almost always want to maintain a registry of objects which own external resources, in order to provide efficient and effective sharing and access. The Dolphin solution to this is a combination of Finalization and Weak References.

N.B. There are similar facilities in other Smalltalks, but they are sometimes less comprehensive and powerful. There are, unfortunately, no standard mechanisms.