# Flexibility

Some time ago, while I was working for a big software house, I heard this (presumably exaggerated) anecdote about how the company had charged a customer \$1 million to upgrade the customer's software. The customer had grown in size, and account codes required five digits instead of four. That was all there was to it. Of course, the client was almost certainly being ripped off, but there are plenty of examples in which a little lack of foresight proves very costly to repair. The Year 2000 problem is a prime example. It pays to allow yourself as much flexibility and room for expansion that can be reasonably foreseen. For example, if you need to pass the number of books as a parameter to a function, why only allow less than 32,768 books (the maximum value of an Integer)? You might also need to allow for half a book too, so you wouldn't want to restrict it to Integer or Long. You'd want to allow floating-point inputs. You could at this point declare the parameter to be of type Double because this covers the range and precision of Integer and Long as well as handling floating points. But even this approach is still an unnecessary restriction. Not only might you still want the greater precision of Currency or Decimal, you might also want to pass in inputs such as An unknown number of books.

The solution is to declare the number of books as a Variant. The only commitment that is made is about the meaning of the parameter-that it contains a number of books-and no restriction is placed on that number. As much flexibility as possible is maintained, and the cost of those account code upgrades will diminish.

Function ReadBooks(ByVal numBooks As Variant)
' Code in here to read books
End Function

Suppose we want to upgrade the function so that we can pass An unknown number of books as a valid input. The best way of doing this is to pass a Variant of subtype Null. Null is specifically set aside for the purpose of indicating not known.

If the parameter had not been a Variant, you would have had some choices:

• Add another parameter to indicate that the number is unknown. A drawback of this approach is that a modification would be required everywhere this function is called. That way lies the million-dollar upgrade. If the parameter were Optional, you would get away with this approach, but only the first time.
• Allow a special value to indicate unknown-perhaps -1 or maybe 32768. We might create a constant of this value so that the code reads a little better-Const bkNotKnown = -1-and use that. This approach leads to bugs. Sooner or later, you or another programmer will forget that -1 is reserved and use it as an ordinary value of number of books, however unlikely that may seem at the time you choose the value of the constant.

If the parameters are Variants, you avoid these unsatisfactory choices when modifying the functions. In the same way, parameters and return types of class methods, as well as properties, should all be declared as Variants instead of first-class data types.

HUNGARIAN NOTATION

The portion of Hungarian notation that refers to data type has little relevance when programming with Variants. Indeed, as variables of different data types can be freely assigned and interchanged, the notation has little relevance in Visual Basic at all.

I still use variable prefixes, but only to assist in the categorization of variables at a semantic level. So, for example, "nCount" would be a number that is used as a counter of something. The n in this instance stands for a general numeric, not an Integer.