Newsletter sign-up
View all newsletters

Sign up for our technology specific newsletters.

Enterprise Java
Email Address:

Java Tip 79: Interact with garbage collector to avoid memory leaks

Use reference objects to prevent memory leaks in applications built on the MVC pattern

  • Digg
  • Reddit
  • SlashDot
  • Stumble
  • del.icio.us
  • Technorati
  • dzone
Object-oriented programs and class libraries often use the model-view-controller (MVC) design pattern. Swing, for example, uses it extensively. Unfortunately, using MVC in a garbage-collected environment such as Java introduces additional serious problems. Imagine, for instance, that your program uses a data model that exists for the lifetime of your application. A user can create views of that model. When he loses interest in the view, he can dispose of it -- or he'll want to dispose of it, at any rate. Unfortunately, the view is still registered as a listener of the data model and cannot be garbage-collected. Unless you explicitly remove every view from the data model's listeners list, you will get loitering zombie objects. The garbage collector can still reach these objects, even though you will never use them and want the garbage collector to discard them.

This Java tip shows you how to use reference objects, introduced in JDK 1.2, to solve this problem. By interacting with the garbage collector, you can eliminate loiterers and lapsed listeners, terms suggested by Ed Lycklama (see the Resources section below for more details). Lycklama generally defines a loiterer as an object that persists past its usefulness. The loiterer category is further broken down into four patterns; most common is the lapsed listener, an object added to, but never removed from, a collection of listeners.

Example problem

In this article, I'll examine a simple Swing MVC application to illustrate how an application using the MVC pattern creates lapsed listeners and memory leaks. Then, I'll show you how to modify the application in order to remove the memory leaks. The example application has a simple data model that contains some strings. The application's main window, shown in Figure 1, lets the user add new strings to, and create new views of, the data model. Both processes are illustrated in the figure below. The application's main window also shows the number of views that are alive, meaning that they are created, but not yet finalized. Each view is a separate frame containing a Jlist, which displays the strings from the data model (not shown here). A view listens to changes in the data model and updates itself accordingly. You will find the full source for this example in Resources.

Figure 1. The application's main window



First, I am going to define the example data model, but not implement it. Then, I'll implement that model's view. Finally, I'll actually implement the data model in four different ways, showing different implementation trade-offs.

Defining the model

The interface VectorModel defines the data model of the example application:

VectorModel.java

 
package mldemo;
import java.util.*;
/**
  * Define a simple "application" data model. You can add, remove, and
  * access objects. When you add or remove an object, all
  * registered VectorModel.Listeners
  * will be notified with a VectorModel.Event.
  *
  * @author Raimond Reichert
  */
public interface VectorModel {
  public static class Event extends EventObject {
    private Object element;
    public Event (VectorModel model, Object element) {
      super (model);
      this.element = element;
    } 
    public Object getElement() {
      return element;
    } 
  } 
  public interface Listener extends EventListener {
    public void elementAdded (VectorModel.Event e);
    public void elementRemoved (VectorModel.Event e);
  } 
  public void addElement (Object object);
  public void removeElement (Object object);
  public Object elementAt (int index);
  public int size();
  public void addListener (VectorModel.Listener l);
  public void removeListener (VectorModel.Listener l);
} 


Whenever an element is added to or removed from the vector, the VectorModel's implementations must notify their listeners.

  • Digg
  • Reddit
  • SlashDot
  • Stumble
  • del.icio.us
  • Technorati
  • dzone
Comment
Login
Forgot your account info?
Add comment
Anonymous comments subject to approval. Register here for member benefits.
Have a JavaWorld account? Log in here. Register now for a free account.
Resources