Article

Revenge of the Old Fogeys?

Revenge of the Old Fogeys?

(August 26, 2002) - For years, the badge of honor for a software engineer was the ability to write fast code that occupied a small amount of memory. In the days when 640K of RAM was a luxury and 10 Mhz clock speeds were considered blazing, this was almost a necessity.

Now that most PCs ship with a minimum of 256MB of RAM and CPUs with clock speeds of 1Ghz or better, the focus has changed. The accolades seem to go to those writing code that is easily understood by developers needing to either support it or, in the case of object-oriented systems, reuse it for another purpose. Developers who honed their skills of developing small and fast code footprints are forced to retrain themselves in the new paradigms.

Enter the wireless device. For the near future, many wireless devices (such as WAP-enabled phones) will have at most 512K of RAM and comparatively slow clock speeds. Suddenly, the old style programmer who can write small footprint code that runs very efficiently is back in vogue.

I think it's great that several of the standard J2SE packages were removed from J2ME, because it forces us in the development world to rethink some of the solutions we've used in the past. We've come to a place where "Old Fogeys" can be of great assistance, having not only read and digested the GoF and other top object-oriented design books, but having actually built and deployed software on a many different platforms using a variety of techniques and languages.

Even Java Developer's Journal, always at the forefront of Java development trends, has gotten on the bandwagon. In the July 2002 issue, an article titled "Java Class Files: Hello World! In 70 bytes" was published. Now, if that isn't old style, I'll eat my Z80.

"We've Done All This Stuff Before. We Can Help."

I fondly remember the time when my group was competing to write a C program that could print out

1 little
2 little
3 little Indians
4 little
5 little
6 little Indians
7 little
8 little
9 little Indians
10 little Indian boys

using less than 100 characters. I never made it to the magic mark, however. I always got stuck at around 104, but it was a great exercise. Anyone want to try this in Java, using the methods shown in the article I referenced above? I'd be interested to see how small some of you could make such a class.

By now, you're probably thinking to yourself, "Why is JavaDevelopersJournal.com bringing us this article and what does it mean to me?" Let me give just a few reasons on the why. Hopefully, the "what does it mean to me" part will become evident soon.

First of all, those developers sitting in a big cube full of old C books and Bell Labs technical manuals aren't necessarily the "dinosaurs" you've pegged them to be. More than likely, they were thinking and writing code using object-oriented techniques before many of today's Java developers did their first "Hello World". Also, studying the techniques they use can prove fruitful for people who know Java, but don't have a lot of real world experience.

I can relate this to a person I worked with, absolutely brilliant in object-oriented design but (having come from an academic background) lacking in production experience, who I overheard saying "CORBA is easy. All you do is write the IDL, write a little code to fill in the methods generated by the IDL compiler, and you're done." I asked him if he'd ever tried to deploy CORBA in a production environment locked down by firewalls and he replied that he hadn't. I told him that if he had, then he'd realize the error he'd made in that statement.

This kind of stuff is where we Old Fogeys come in. We've done all this stuff before. We can help. Let us.

For example, look at the class diagram shown in Figure 1.


Figure 1

This class diagram is from an actual design that I saw in a previous life. Isn't this rather a bit of overkill? If you don't think so, and you could be right given the correct set of circumstances, read on to get the full story.

When I asked which of the objects/interfaces were actually instantiated or used when casting, the reply was the object called ActuallyUsedBizObject and Interface5. I asked why all the other interfaces and classes (both abstract and not) were built, if none of the sub-classes were ever instantiated or cast to be one of these superclasses.

Also, why do two of the classes implement the same interface? Wouldn't inheriting from the superclass pick up the interface? I got the deer in the headlights look and got a reply of "Well, you just don't understand object-oriented design." Maybe I don't, but going down a tree of 4 classes and 4 interfaces was sure a pain when trying to find where a method was actually declared. And on top of that, the objects were all in different packages, which means they were in different directories when I tried to find them. Not a very pleasant experience

Introducing: Lanny's Laws of Java, #1 - #5

Which brings me to Gilbert's First Law:

  • Don't build up a multi-level inheritance tree just because you can.
If you are only going to cast to one or two interfaces or classes, don't write a huge chain of base classes, then a class on top of that implements an interface, etc., etc. It's harder, not easier, to maintain that way, and it's much harder to find what a given method does.

Besides, if you are going to be working in a RAM-limited environment, such as most of the J2ME-capable devices, why do you want to use up all of your space writing a complicated inheritance tree when you don't need to? Wouldn't that space be better served with a nice graphic or something?

Allow me to shift gears here a second and discuss refactoring. Much of the refactoring going on today is either to enhance readability or to introduce tried and true patterns into the software. Also, a lot of the refactoring is being done under the auspices of the Extreme Programming (XP) paradigm. J2ME brings in another refactoring element, that of execution speed and class file size, which is where we old fogeys can help immensely.

If you're going to try out the XP thing, here are a couple of tips to keep in mind, starting with Gilbert's Second Law:

  • XP doesn't work unless your whole group is involved
I was once part of a 7-person team charged with pioneering the use of XP in the company I worked for. Only problem was, there were 3 people doing what I called "XP within XP." They sat together a couple of times per day and decided how they would change the base code, usually without any kind of user (meaning business or architecture folks or anyone else in out group) feedback. They would then spend the next few hours, usually up until around 8 p.m., changing code and running JUnit tests.

I, being an old fogey, was working a standard 8 to 5-ish schedule. I would come in the next day and all of my code would be broken and I had to wait until 9:30-ish until one of the three guys came in to tell me what they'd done. The upshot of all this is that I'd waste around 2 hours per day because I (and three others in the group) weren't kept in the loop as to what was changing and what I needed to do in order to keep up.

If you're going to do XP, everybody has to be on board with the process, working together, and keeping similar schedules. The concept of core hours, which has been around forever but was seemingly abandoned in the go-go-go dot-com era, could really help out a lot here.

Next comes Gilbert's Third Law:

  • XP doesn't work if you change things just for the sake of changing them
Referencing the same group I mentioned above, we were in charge of building objects that could be used easily from JavaServer Pages. To do this, we wanted to have interfaces that were easily understood and methods in those interfaces that were named something close to what the method actually did. So, with that assumption in mind, I built all of my interfaces and placed them in a design document which was OKed by my team and the business folks who'd written the requirements.

Fast forward to a couple of months later. I came into work one morning and began to do a complete pull from the source code repository (I had gotten to the point where it was easier than waiting on someone to come in and tell me what had changed after I left the night before). I fired up my JUnit tests and nothing worked.

So, I started poking around in the code and noticed that every single one of my methods had been renamed. I waited until the person who had changed them came to work and asked why he had changed the method names. I got a response of "Well, it made more sense to us." When I asked if 'us' included any of the people who had written the requirements or had signed off on the design document, I got that deer in the headlights look again and a "Well, that's the way XP is. You change things as you come to them" answer.

Sorry, but it doesn't work that way. I don't believe that changing interfaces just because you think they're named wrong is a correct application of XP. Not only did I have to change my test code and my design document, the folks working on a reference implementation of the JSPs had to go in and change all of their code. Not a good thing. It cost about 24 man-hours to complete all the modifications caused by what this guy did on a whim one night.

Refactoring is a great thing and should be a part of any ongoing software project. Just keep in mind that with J2ME, you must include the RAM size and processor speed of J2ME-capable devices in mind when rewriting the code.

While I'm still on the methodology bandwagon, let me suggest something -- Gilbert's Fourth Law:

  • Use the "Requirements" phase of the Rational Unified Process (RUP) to front-end your Extreme Programming process
By this, I'm talking about using the following RUP steps (in more or less chronological order):
  1. Analyzing the problem
  2. Understanding Stakeholder Needs
  3. Defining the System
  4. Managing the System Scope
  5. Refining the System Definition
At this point, you should have use cases for your whole system, a system requirements document that is at least a stake in the ground you can begin your prototyping from, and a software requirements document that provides a roadmap for your XP development. This is especially important in larger companies, when you have several organizations competing for development time and resources and they all have different ideas of how a given system should work.

I'm not suggesting a total embrace of either RUP or XP, just picking and choosing from the strengths of both.

One last point that will help you in building J2ME apps is Gilbert's Fifth Law:

  • Don't use delegation just because you can.
This is something that has bugged me since the old days of structured "top-down" programming, when I had to walk 5 miles uphill (both ways!) in the snow to get to the only punch card reader in town. A developer wants to make sure that their methods (or procedures as we used to call them way back when) aren't very big, so they put a little bit of code in several methods and have them call each other. Why do they do that?

Here is a perfect example:

public int method1 (String parm1) {
<some code>
return method2(parm1,null);
}

private int method2 (String parm1, String parm2) {
<some more code>
return method3(parm1,parm2,null);
}

private int method3(String parm1, String parm2, String parm3) {
<some code to finally return an int>
}

Again, I've actually seen this in production code. There could be cases, such as when the methods were all public and were exposed in an interface, where this is perfectly valid. But, in this particular instance, I asked the person who built this three questions: (1) Are method2() and method 3() called anywhere else? The answer was no. (2) Are there any plans for method2() and method3() to be made public? The answer was again no. (3) Why was the code written this way? The answer was "To make it past code review. A method can't be more than 10 statements long, according to our standards."

True story. Yet, many so-called "lead engineers" or "chief programmers" will swear up and down that you need to write code this way for it to be understandable. Did I mention that the 3 methods were part of a 500 line source file and that they weren't lined up in order, so you had to do a search all over the file to try and track down what was actually returned from method1()? Doesn't seem more understandable to me and it was a pain to track this down. In the J2ME world, try and avoid stuff like this at all costs. You need the space and speed for something else.

What Goes Around Comes Around

Ah, well.. Time to get off the soapbox and close. I just finished reading an article about companies who were vilified in the '90s for not joining the buyout and merger mania so common to the dot-com bubble. Now, they're the ones with all the cash. Same with us old fogeys. We kept our heads down and learned new things, just like we always have, when everyone else (well, not everyone, but it sure seemed like it) was out drinking the dot-com KoolAid and quickly slapping out reams of code in the hopes that something would stick.

Look at us now. In demand, management and marketing (wanting something tried and true, not something flashy that might possibly work) looking to us for help. We know how to build small, fast code (regardless of development style or paradigm) and are ready and willing to do so.

Just like platform shoes and bellbottoms, what goes around, comes around.

*Do you agree with "Lanny's Laws"? Or disagree violently? Or anything inbetween. Let us know here.

More Stories By Lanny Gilbert

Lanny Gilbert, currently a Senior Enterprise Architect at Cingular
Wireless, has been a developer and architect in the telecom
arena for over 18 years. He has filed 10 patents, involving AIN (Advanced
Intelligent Network) and messaging, and has 12 more in various stages
of development.

He is a Sun Certified Java 2 Programmer and is currently working on the
Sun Certified Web Component Developer certification. You can reach him
via e-mail at [email protected]

Comments (11)

Share your thoughts on this story.

Add your comment
You must be signed in to add a comment. Sign-in | Register

In accordance with our Comment Policy, we encourage comments that are on topic, relevant and to-the-point. We will remove comments that include profanity, personal attacks, racial slurs, threats of violence, or other inappropriate material that violates our Terms and Conditions, and will block users who make repeated violations. We ask all readers to expect diversity of opinion and to treat one another with dignity and respect.