All | BASIC | Personal | Sun
Main | Programming Accident... »
20060305 Sunday March 05, 2006

Programming Accidents (aka Bugs) I remember reading a magazine for private pilots a couple of years ago and there was a column analyzing accidents. The idea was to learn from the mistakes other pilots had made and ultimately help the readers to become better, safer pilots themselves.

In the undoubtedly error prone programming business, bugs are all too often just fixed and then forgotten. Rarely is any time spent on reflecting about what caused them and sharing any of the experiences with other programmers. But that is going to change today as I will share the following programming accident that happened to me last week.

I started out with a program that looked roughly like this:

class A extends B
{
    A(int...aarr)
    {
    }

    public static void main(String args[])
    {
        A a = new A(1, 2, 3, 4, 5);
        a.print();
    }
}

class B
{
    int array[];

    B(int...barr)
    {
        array = barr;
    }

    void print()
    {
        for (int i : array)
        System.out.println(i);
    }
}

The source compiled fine and when running it, I expected it to print the numbers 1 through 5, but of course, nothing was printed at all. The program didn't crash either; it just didn't print any numbers. After a little bit of debugging I saw that the content of a.array was an array of length 0 rather than the array of length 5 that I was expecting. So what happened? Where did my numbers disappear to?

When a Java compiler generates bytecode for a method with a variable length parameter list (as in the constructor for A) it actually creates an array of the formal argument type and with the number of actual arguments and copies the actual arguments into that array. If there are no actual arguments passed for the variable length parameter list, the compiler generates an array of length zero. That means variable length parameter lists are nothing but some compiler magic allocating arrays, filling them with the actual arguments and passing those arrays in place of individual arguments.

In the above example the array arrived at the constructor of A but was never passed on to the constructor of B because I forgot to add an explicit "super(aarr)" call at the beginning of the constructor. But since the superclass constructor for B also accepts a variable length parameter list, the compiler silently assumed that I meant to write just "super()", which the compiler inserts for you if there is no explicit call to the superclass constructor. But "super()" can be interpreted as a call to a superclass constructor with a variable length parameter list, which is what the compiler did. It created a zero length array for the variable length parameter list, which was then assigned to the array field of B in its constructor. And that's why my program didn't work. Before Java added variable length parameter lists to its language, the compiler would have raised an error because it would not have been able to find a matching constructor.

Could it be that this is a bug in the compiler? Let's take a look at the the Java Language Specification. Its 3rd edition says in §8.8.7, "If a constructor body does not begin with an explicit constructor invocation and the constructor being declared is not part of the primordial class Object, then the constructor body is implicitly assumed by the compiler to begin with a superclass constructor invocation “super();”, an invocation of the constructor of its direct superclass that takes no arguments." Well, the constructor B(int...barr) is a superclass constructor taking zero or more arguments. Therefore the compiler is behaving correctly.

It remains to be asked, how can this pitfall be avoided in the future? I haven't really found a great solution except to be careful when defining a constructor that takes no other parameters except a variable length parameter list.

Happy programming!

Posted by herbertc ( Mar 05 2006, 10:15:00 PM PST ) Permalink Comments [0]

Trackback URL: http://blogs.sun.com/herbertc/entry/programming_accidents_aka_bugs
Comments:

Post a Comment:

Name:
E-Mail:
URL:

Your Comment:

HTML Syntax: NOT allowed

HerbertC's Blog






Calendar

RSS Feeds

Search

Links

Navigation

Referers