CSC/ECE 517 Fall 2007/wiki3 8 42

From Expertiza_Wiki
Revision as of 19:53, 19 November 2007 by Mbsimmon (talk | contribs) (Added CRP.)
Jump to navigation Jump to search

Introduction

The objective of this document is to introduce a series of design patterns developed by Robert C. Martin (Uncle Bob) that relate to packages.


Robert C. Miller defines the domain of design patterns to be the architecture of systems modules (packages, classes and components) and their interconnections. He sites the need for design patterns being to address the four major reasons that designs 'rot,' rigidity, fragility, immobility and viscosity.


  • The RIGIDITY phenomenon occurs when software managers become reluctant to address minor changes because fixing them inevitably causes other defects due to design flaws, which may end up being more numerous and severe than the original defect addressed. The result is that the software becomes rigid – it does not change as change is needed.
  • The FRAGILITY phenomenon is similar to rigidity in that the software system is so poorly designed one small defect fix or enhancement leads to numerous other defects. In fact, software rigidity is a direct result of software fragility.
  • Software IMMOBILITY occurs when software is either coupled so tightly or encapsulation is so improperly managed that the system, component or module can't be used in either other systems or the current system in other places.
  • VISCOSITY (of design) is a quantitative or estimated measure of how easy it is when making a change to follow good design principles vs. implementing a hack. If it is always easier to implement a hack, viscosity is high.


The following design principles are designed to avoid the pitfalls associated with the above four reasons of unsuccessful software engineering. The first three are concerned with the cohesion of packages – how they are stuck together or constructed. The last three are concerned with the coupling of packages, or the degree to which they rely on each other.


Reuse/Release Equivalency Principle

The granule of reuse is the granule of release. Only components that are released through a tracking system can be efficiently reused.


The idea behind this principle is based on client needs. It should not be expected of a user to upgrade the system whenever the designer implements a change to an external component. Because upgrading is sometimes a slow process with a high potential for difficulties that need to be managed, it is usually a process that is implemented with a great deal of care – and sometimes avoidance. Because of this, authors that don't implement a release system and ensure that older versions of a system are maintained for a period of time don't support reuse in that the demand for their components will decrease greatly.


To illustrate this principle, consider the third-party image processing libraries provided by Leadtools, Inc. These libraries and modules are release controlled and the company provides release support for various versions up to a specified time limit in the past. The reason for this is clear – without a release tracking mechanism users of their libraries would be forced to constantly upgrade as both major and minor changes were implemented. As upgrading can be a painful process, this type of solution would be less than ideal and users of Leadtools libraries would get their support elsewhere because the software would effectively be non-reusable.


Common Closure Principle

Classes that change together belong together.

This principle is concerned with the design of groupings of classes, or how packages should be organized. Experience has taught that the amount of testing required for a new release of a system is proportional to the number of packages that were changed in that system. If a package is changed, all functionality using that package must be tested regardless of whether individual classes within that package were utilized (this is due to the fact that classes can send messages to each other).


The common closure principle requires a bit for foresight and experience as it suggests that packages should encompass classes that are likely to change together. Doing so minimizes the number of packages that are effected by a change and therefore minimizes and adverse effect on a system as a whole as well as decreases the scope of required testing. In doing so, the effect of changes is minimized.


This type of thinking requires both experience and a good understanding of the environment in which the target system will be employed. When environment knowledge is limited, end users may be a good source as to the most likely changes that will occur to a system in the future (which is to say, if you don't know – ask).


Common Reuse Principle

Classes that aren't reused together should not be grouped together.

This is another principle concerned with the grouping of classes into packages. The idea behind this principle is that classes which provide the same 'reuse' functionality will more than likely be used under the same set of circumstances. For example, consider an application that maintains information about patients in a Patient object. Certainly other objects will interact with Patient objects – Insurance objects, Employer objects, etc. Because these objects are likely to be used in concert with each other, they should be packaged together.


Consider what would happen if the class PatientCollection – which maintains a list of Patient objects as well as performs various operations on those Patient objects) were placed into Package A, but the Patient, Insurance, and Employer classes were placed in Package B. If this functionality set changes, both Package A and Package B change. As previously stated, when packages are changed, all code which uses those packages must be re-validated. If Package A also contains functionality used elsewhere in the using system, the validation required has been greatly increased.