Previous Section  < Free Open Study >  Next Section

7.4 Deciding Between a Containment and an Association Relationship

Heuristic 7.1

When given a choice in an object-oriented design between a containment relationship and an association relationship, choose the containment relationship.

This choice is not always available. The association examples that we have looked at must be association; they cannot be containment relationships. In an object-oriented design, it sometimes happens that we are given this choice. Consider the home heating system problem posed in Booch's object-oriented design text [7]. In Section 3.4, we examined the notion of rooms deciding that they need heat, informing a heat flow regulator, which turns on a furnace, etc. There is the additional requirement that once heat is available, when the furnace has hot water to flow through the pipes, the water valve to the room requiring heat must be opened. The key question is who should open the valve. Two possibilities come to mind:

  1. Each room contains its water valve.

  2. The furnace contains all of the water valves.

In the first design, after a room decides it needs heat, it tells the heat flow regulator to get heat. The heat flow regulator then asks the furnace to provide heat; the furnace informs the heat flow regulator when heat is available; the heat flow regulator tells the room that heat is available; the room tells the valve to open; and, finally, the valve opens (see Figure 7.4).

Figure 7.4. Home heating system with indirect uses relationship.


This is an extremely roundabout design. Some designers argue that since the furnace knows when the valve can open, the furnace should tell the valve to open when heat is available. This implies that the furnace contains the valves. The design that follows from this premise is much cleaner and more direct, as Figure 7.5 shows.

Figure 7.5. Another possible design for the home heating system.


How does the furnace know which valve to open when heat is available? Obviously, someone has to tell it. The heat flow regulator can pass the name of the room as an explicit argument, and each valve could contain the name of the room to which it is associated. The furnace could perform an easy search through the valve's room attribute until it finds a match. It is important to note that in this design the name of the room is a referential attribute of the valve class. What is the relationship between the Valve class and the Room class? In this design it is an association relationship. There is no direct uses relationship between the two classes; the furnace acts as the third-party class. These two designs bring up an interesting point. Should the room contain a valve, or should it be associated with a valve? The heuristic states that containment is the better design, but in this example we have seen that the association model gives us a cleaner design with more direct uses relationships. What is the problem with using association instead of containment?

Consider the task of constructing a new Room object. In the first design, the constructor for the room knows implicitly that it must build a valve since the containment relationship states that each room must have a valve. In the second design, users of the Room class must know by convention that constructing a new Room implies building a Valve object and giving it to the Furnace. Not only are developers required to follow this convention, but Rooms are now unnaturally dependent on, and aware of, the implementation of Furnaces. This is the key problem with choosing associations over containment. Association relationships build conventions into the design, and users of the classes need to know these details. The containment relationship creates implicit and hidden implementation details that users of the class do not need to know. Given this information, the first design is the better choice, despite the need for some roundabout uses relationships.

    Previous Section  < Free Open Study >  Next Section