Sunday, May 17, 2009

The Summer Project 2009, Part 2: Notes on Design Methodology

A great deal of what we call programming is actually breaking down large concepts or problems into smaller ones (a.k.a. decomposition or factoring) and hiding details behind generalization (a.k.a. abstraction). Programmers wield these conceptual weapons against the dread beast complexity, and with our first attempt at requirements in hand we can start to see how they apply in practice. Formally, what we are talking about is how to go from Requirements to Design.

One of the most basic methods we use on initial approach to a problem is to break it down into "things" and "actions." For instance, from our requirements we have several things: account, transaction, category, monetary value, statement, and report. These are the nouns in the language of our problem. The actions are the verbs in that language. Our example has enter, assign, edit, void, reconcile, generate, etc. Notice that the verbs don't really have any meaning without acting on one of the nouns: enter a transaction or generate a report, for example. This is the basic insight behind a style of programming called Object Oriented: every action is tied to the thing being acted upon. (A sentence's verb acts on its object, whence object oriented). You build a program by implementing the objects and their interactions. Most objects have one or more special methods called constructors to create concrete instances of the thing the object describes. To create a transaction, you provide all the necessary data to a transaction constructor which returns an instance of the transaction object with the data you specified stored as fields within the object instance. To add that transaction to a particular account you would tell the account object to add a transaction, passing the transaction object instance to it as part of the command. Object orientation descends from the general theory of imperative programming, a paradigm that describes things via a series of command statements that cause changes to the system.

Of course, the objects and actions view of imperative programming isn't the only way to operate. For example, entity-relationship modeling is how database based systems are constructed, and it descends from the theory of declarative programming. Instead of a program issuing a series of commands to produce the result, the program states the information it wants without regard to how it actually goes about getting it. For example, the form would be similar to this: 'I want the total monetary amount spent under the medical category,' or 'get all transactions from the checking account for the last thirty days.' While this method may sound simpler, it isn't necessarily, and it requires greater infrastructure. (It has to be built on top of something that actually knows how to do the calculations necessary to get the results, usually a relational database management system.)

I can take an educated guess that most of the dedicated applications back in part 0 use the entity-relationship method of looking at the data. But for us at this point, there is no right or wrong choice. Either path will inform how the program is ultimately built. For the purposes of this series, I'm going to start out with the Object Oriented method. Next time, we will actually begin creating a design from our requirements.

No comments: