views:

539

answers:

8

I have a question about the syntax of the Java main declaration:

public static void main (String[] args)

Since you can pass a variable number of Strings when invoking the main function, shouldn't this be a variable length argument list rather than an array? Why would a command-line invocation of this method with a list of string parameters even work? (Unless there is behind-the-scenes processing that builds an array with the list of strings and then passes that array to the main method...?) Shouldn't the main declaration be something more like this...? -

public static void main(String... args) 
+15  A: 

main(String... args) and main (String[] args) are effectively the same thing: What you're getting is a String array. The varargs is just syntactic sugar for the caller.

I guess as you never call main() from code, it wasn't retrofitted when varargs were introduced.

Edit: Actually, scratch that last sentence. main(String... args) is perfectly valid syntax, of course. The two styles are completely interchangeable. This works just fine:

public class Test {

    public static void main(String... args) {
        System.out.println("Hello World");
    }

}
Henning
So when you execute a program from command line, you're not actually directly calling the main? There's some processing that occurs before the main is executed? (i.e. building the array from the strings passed)
froadie
They are not same. One cannot call `main (String[] args)` as `main("aaaa")`.
fastcodejava
You're not invoking the main() method using Java. The runtime invokes it for you.
Tim Jansen
"never call main() FROM CODE" :). And no. You cannot call a Java method from a command line. In fact a command line is a program that parse your command, tells the OS to execute some program with a bunch of args, and that program (java.exe by example) load a lot of things into memory (class definitions, etc), creates a Java friendly representation of the system program execution args the command line received, and finally calls the main method. So... no. You're not actually directly calling the main.
helios
re: "never call main() from code" - CAN you call main from code??
froadie
I don't have much of an opinion on calling main from code--it doesn't seem like something you'd want to do much, but in certain situations it should be perfectly valid (for instance, causing one program to run either from within another or as it's own entity). @helios do you have real life experience or even theoritical examples where this was a problem?
Bill K
Of course you can call "main" from code, and it may make perfect sense to do so. Consider for example a Java utility to invoke "main" in a series of one or more classes. How would you write that? Another example is in writing Ant tasks that glue onto existing Java (command-line) utilities.
Pointy
@Bill K: I was just quoting part of the answer. @froadie made his first comment and a pointed at that part of the answer. It was like "Henning said 'FROM CODE'". Next part was: command line is related to main execution of course but it's not a Java method call so it will be related and designed to mimic each other but it doesn't have to have a particular form.
helios
+7  A: 

The main method was designed for Java 1.0.

The "..." syntax was introduced in Java 1.5

It's implemented via an array of the type you defined (my guess, but... if Java 1.4 and 1.5 byte codes are compatible so it must be implemented with arrays).

helios
+1  A: 

The java main syntax predates varargs, which were only introduced in java 1.5.

Steve B.
A: 

Well, the 2nd syntax is just a variation of 1st and yes it would be nice but it's not built into Java at this point

DroidIn.net
A: 

Why do you care? Nobody calls the main method by hand. It is internal to Java.

EDIT : I guess it doesn't matter now as you can define main method as :

public static void main(String... args);

My point is still valid as no one calls main explicitly.

fastcodejava
It makes no difference to how I code. I was just interested.
froadie
unless you call the main method of another class from your current class... You might want to do that, after all.
piggles
I call "main()" explicitly - theory destroyed
Pointy
+4  A: 

There is no Java's main method, in fact you can declare the array as a vararg in your main method:

public static void main(String... args) { System.out.println("Hi!"); }
Fabian Steeg
Interesting. Judging by the other answers/comments, I guess this new main declaration syntax was added with Java 1.5. So the Java runtime determines, based on your main method declaration, whether to pass the strings directly to the main or build an array first?
froadie
Varargs were introduced in Java 5 as syntactic sugar for arrays, meaning they hide the actual array, but underneath, it is the same thing, which is why this works. See also http://java.sun.com/j2se/1.5.0/docs/guide/language/varargs.html
Fabian Steeg
No. It always builds an array. It's just a different syntax for expressing the exact same underlying code. Java will still parse the command line args into a string array, load the referenced class, find it's main method, and call it with the args.
Yuliy
@froadie: No, it always builds an array. `String... args` == `String[] args`, as far as the called method is concerned. The parameter is an array in any case.
Henning
+1  A: 

Shouldn't the main declaration be something more like this...?

public static void main(String... args) 

Actually, that could be done without a problem.

It was String [] args before var args were introduced but nowadays both work.

OscarRyz
+6  A: 

You can declare main either way, and it works just fine. There are no "backward compatibility" or "retrofitting" issues. However, readers of your code may find it distracting, and it is unlikely to improve your program in any way.

The Java Language Specification (third edition) section 8.4.1 says that "If the last formal parameter is a variable arity parameter of type T, it is considered to define a formal parameter of type T[]".

The specification for how a Java program starts up is in JLS 12.2, which references chapter 5 of the VM spec. The VM spec section 5.2 says that the VM invokes a public class method "void main(String[])". Since the VM spec has no concept of variable arity, a main that was declared using "..." satisfies the requirement.

Neal Gafter