XML.com: XML From the Inside Out
oreilly.comSafari Bookshelf.Conferences.

advertisement

Design Patterns in XML Applications
by Fabio Arciniegas A. | Pages: 1, 2, 3, 4, 5, 6

Contents

Design Patterns in XML Applications
Command Pattern
Flyweight Pattern
Wrapper Pattern
Iterator Pattern
Bibliography

Synopsis

Flyweight is a structural pattern used to support a large number of small objects efficiently. Several instances of an object may share some properties: Flyweight factors these common properties into a single object, thus saving considerable space and time otherwise consumed by the creation and maintenance of duplicate instances.

Structure

Flyweight Pattern Structure
Figure 4. Flyweight Pattern Structure

XML Context

One of the biggest problems with keeping the DOM representation of the document, instead of constructing your own objects from the output of SAX (or another event-oriented interface), is the size of the representation. In this discussion we assume not only that you want to roll your own domain-specific objects, but that you want them to be as space-efficient as possible.

Suppose you are writing a SAX-based application that constructs CD objects from a file called musicCollection.xml. At the end of parsing you might want a collection of CD objects to be created. Those objects may look like:

Initial CD structure
Figure 5. Initial CD structure

As you probably already noticed, all the information about the artist (in this example we use only one, for simplicity) may be replicated many times. (Notice too that this artist information is unlikely to change over time.) This is a clear candidate for factorization into what we'll call a flyweight: a fine-grained object that encapsulates information (usually immutable) shared by many other objects.

Remember that CD objects should be constructed from an XML file that might look somewhat like this:

       <?xml version="1.0"?>
       <collection>
          <cd> <!-- This is quite simplistic, better XML
             representations could have been
                    chosen, but it only aims at
                    illustrating the pattern -->
     <title>Another Green World</title>
     <year>1978</year>
     <artist>Eno, Brian</artist>
   </cd>
          <cd>
     <title>Greatest Hits</title>
     <year>1950</year>
     <artist>Holiday, Billie</artist>
   </cd>
          <cd>
     <title>Taking Tiger Mountain (by strategy)</title>
     <year>1977</year>
     <artist>Eno, Brian</artist>
   </cd>
       </collection>
       

You decide to use Java and a SAX parser to do the job. Now you must construct a set of SAX handlers capable of creating CD objects with flyweight artists. This will be the subject of our example.

Example

The basic logic for the SAX handler is simple:

  • Whenever a CD open tag is found, create a new CD object.

  • Whenever title or year elements are found, enter them in the current CD.

  • Whenever an artist element is found, ask the artist factory to create it. This is fundamental to the problem: the CD object does not know if it is sharing this object with others; only the factory keeps track of what has been created.

The following code illustrates a simple factory for the extrinsic objects, and the output produced by the example program if run with the above XML file.

Flyweight Example: Factory

// Simple Flyweight factory for Artist classes (Artist is the extrinsic,
// flyweight class. CD is the client)

import java.util.Hashtable;
import java.lang.String;

public class ArtistFactory {
    // Whenever a client needs an artist, it calls this method. The client
    // doesn't know/care whether the Artist is new or not.

    Artist getArtist(String key){
 Artist result;
 result = (Artist)pool.get(key);
 if(result == null) {
     result = new Artist(key);
     pool.put(key,result);
     System.out.println("Artist: " +key + " created");
 }
 else
     System.out.println("Artist: " +key + " reused");
 return result;
    }
    Hashtable pool = new Hashtable();
}
      

Flyweight Example: Output

      $ java -Dorg.xml.sax.parser=com.ibm.xml.parser.SAXDriver \
      FlyweightDemo music.xml
      Artist: Eno, Brian created
      Artist: Holiday, Billie created
      Artist: Eno, Brian reused
      Artist: Eno, Brian reused
      Artist: Eno, Brian reused
      

For the complete code, please download flyweight.zip

At the end of the parsing, the actual object structure will be:

Flyweight Example: Factory
Figure 6. Flyweight Object Diagram - Example

Summary of Common XML Uses

The flyweight pattern is useful in XML applications when:

  • You have a domain-specific representation of your document, and you want to keep it as small as possible by taking advantage of shared information among objects.

This is often the case!

In this section we analyzed Flyweight, a structural pattern useful in event-based XML applications. In the next section, we will examine Wrapper, another structural pattern, also in an event-based context.

Pages: 1, 2, 3, 4, 5, 6

Next Pagearrow