Newsletter sign-up
View all newsletters

Sign up for our technology specific newsletters.

Enterprise Java
Email Address:

Java Tip 62: Explicit and recursive programming in Java

Use Java style and idioms to ease maintenance without sacrificing performance

  • Digg
  • Reddit
  • SlashDot
  • Stumble
  • del.icio.us
  • Technorati
  • dzone

Page 2 of 3

Addressing the problem

Now that we have examined some of the problem areas with this routine, let's explore ways to address each of those contentious areas.

First off, let's replace the recursion with an explicit while loop that checks for the stopping conditions described earlier. Next, we'll introduce a temporary Frame reference, which will be set inside the loop when we find the the parent Frame object. Note that we set the temporary to our default return value of null. Also notice how the new version of the routine only has a single return statement at the end.

static public Frame GetFrame(Component component)
{
Frame  resultingFrame = null;
while (component != null && resultingFrame == null)
        {
        if (component instanceof Frame) resultingFrame = (Frame)component;
        else  component = component.getParent();
        }
 return resultingFrame;
 }


Okay, for you byte counters out there, this version does result in three additional bytecode instructions than the original, recursive version has -- 19 versus 16. However, the new, explicit form never has to worry about running out of stack space -- the routine is using a single stack variable, resultingFrame, rather than relying on the method invocation stack. This explicit management of the stack data not only results in faster code in general but is also much more conducive to the optimization efforts of native Java compilers, JIT compilers, and so on.

The greatest benefit of this new, explicit version is the increased readability, simplicity, and maintainability of the code. So, we have created a version that is safer (no call stack limitations), faster (explicit looping rather than recursion), and clearer about what it's really doing.

Taking the routine a step further

We've gone this far in modifying the original, why stop here? Why don't we make the routine more useful too? In other words, why should we settle for a routine that only looks up Frame parents of a Component? Rather than writing a new routine for each type of parent that we may want to look up, let's just make the routine more generic in what it's searching for!

There are many ways to make this routine more generic. We can make it generic along a number of dimensions including the containment hierarchy and the target parent specification. In this particular case, we are going to limit this routine to sticking to the component container hierarchy but allow the caller to specify the target parent class.

First, here is an example of how you would use the new method to determine a button's parent which is an Applet.

Applet  dadApplet = (Applet)GetParent(myButton,"Applet");


In this new version we replace the use of the instanceof operator with a bit of object introspection:

static public Component GetParent(Component component, String compType )
{
Component  resultingComponent = null;
while (component != null && resultingComponent == null)
        {
          if ( compType.equals( component.getClass().getName() ) )
                        resultingComponent = component;
        else  component = component.getParent();
        }
 return resultingComponent;
 }


In terms of bytecode instructions, we have introduced one more invoking bytecode because getClass().getName() yields two "invokevirtual" calls -- whereas the statement instanceof has it own special single bytecode. Seems like a pretty reasonable tradeoff given that our routine is now a fair bit more generic.

  • Digg
  • Reddit
  • SlashDot
  • Stumble
  • del.icio.us
  • Technorati
  • dzone
Comment
Login
Forgot your account info?
Add comment
Anonymous comments subject to approval. Register here for member benefits.
Have a JavaWorld account? Log in here. Register now for a free account.
Resources