Agile processes use a just-in-time approach to design, coupled with a highly disciplined approach to integration and automated testing.
Traditionally, large scale design work in the early days of a project frequently has to be repeated, or redone, in the light of later knowledge. In a typical project fewer than 20% to 30% of the original requirements will be implemented in their original form. When those requirements change later in the project this incurs enormous extra cost. In contractual environments where money will change hands this is gleefully referred to as a 'scope change'. Many long and expensive meetings are held to determine how much more money must change hands.
Agile methods complete enough design work to support the forthcoming iteration, no more. This avoids the common tendency to over-engineer features. Agile development promotes creating smaller, better targeted, more re-usable units. These smaller units are built using extensive automated tests. When the customer requires a feature change in a later iteration, the comprehensive use of automated tests ensures that the change is contained and does not impact on other parts of the project.
Overall the agile approach brings huge savings to a project.
- The development team avoids spending months creating excessively detailed specifications that are reworked before they are implemented
- Business benefits are realized months earlier
- Working, implemented, software, in production use, informs the process of deciding what should go into later iterations
- The customer no longer has an incentive to delay the start of the project until every conceivable requirement is accounted for. The customer knows that (s)he can change direction at every iteration
- There is NO cost, or time, penalty if the customer changes his/her mind on an un-started feature. The design and development work has not started yet - there cannot be any loss
- The software is supple enough to change direction with business requirements. If business requirements change, the project can move to a new direction no later than the start of the next iteration