5

Why does varargs have to be the last parameter in method signature?

I want to know the reason.

mikera
  • 105,238
  • 25
  • 256
  • 415
Sam
  • 6,770
  • 7
  • 50
  • 91
  • If thats not the way, then in the method usage, how can the compiler find out where the varargs end and next method arg begins? – Santosh Feb 21 '12 at 06:04
  • The varargs can be distinguished by first identifying the non-varargs and taking the rest as the varargs irrespective of whether they appear at the start or the end. Currently if there are five arguments with the last one as varargs then it is resolved as whatever comes after the fourth is the varargs. This can be reversed also like if there are five arguments with the first as varargs, resolve from end to start, like the last four are normal and whatever is there excluding the last four are part of the first vararg :) I think it's just implemented this way since there is no real need till now – prajeesh kumar Feb 21 '12 at 06:35
  • See the interview with `C family of language` creators here [ C Family Interview](http://www.gotw.ca/publications/c_family_interview.htm) where Gosling says "I had this personal rule that by and large I didn't put anything in just because I thought it was cool. Because I had a user community the whole time, I'd wait until several people ganged up on me before I'd stick anything in. If somebody said, "Oh, wouldn't that be cool," by and large I ignored them until two or three people came up to me and said "Java ought to do this." Then I'd start going, well, maybe people will actually use it." – prajeesh kumar Feb 21 '12 at 06:39

2 Answers2

16

Because it makes the compiler's life simpler. There's no real reason why it couldn't have more arguments after, but it would require a much more complex compiler and so the spec was written that way.

Ignacio Vazquez-Abrams
  • 776,304
  • 153
  • 1,341
  • 1,358
  • 1
    Thanks for your answer, but by above comments I think this not possible,for sample: 'public void test(String...names,String code)', compiler can't distinguish between names and code parameter. – Sam Feb 21 '12 at 06:16
  • 2
    Yes it can. It counts all of the arguments, sticks the last in `code`, and all the others in `names`. – Ignacio Vazquez-Abrams Feb 21 '12 at 06:17
  • You are right to say that "varargs must always be last" makes the Java compiler team's work much easier. However, this isn't really a parsing issue, since the parser generates ASTs. This rule just makes a whole lot of other parts of the compiler, such as overload resolution, much easier. – Adam Mihalcin Feb 21 '12 at 06:21
  • @Adam Mihalcin I don't know AST concept,please discuss more and its relation with varargs issue. – Sam Feb 21 '12 at 06:26
  • 1
    @MJM The definition of an AST is outside the scope of your question, but here's a comment-sized explanation: a compiler is divided into a lexer that tokenizes the source code, a parser that builds abstract syntax trees (ASTs) from the tokens, an optional type checker and optimizer that operate on ASTs, and a code generator to convert those ASTs from some internal representation into bytecode. See http://en.wikipedia.org/wiki/Compiler for an overview of how a compiler works. – Adam Mihalcin Feb 22 '12 at 00:12
10

The main reason is because it would be potentially ambiguous otherwise....

For example, how could the compiler tell whether arguments are varargs or separate named arguments in a long list of arguments with multple varargs?

Imagine a method signature like:

printNames(String... girls, String... boys);

If you do printNames("Lucy", "Jo", "Paul") is Jo a boy or a girl?

As another example of ambiguity, having varargs earlier in the argument list could cause problems when there are overloaded methods. For example:

printFruit(String... apples, String orange);
printFruit(String... apples, String grapefruit, String orange);

How can the compiler tell whether the second-to-last argument is a grapefruit or an additional apple?

Note that this isn't unique to Java, most languages that support varargs only allow then to be at the end of the argument list for the same reason.

mikera
  • 105,238
  • 25
  • 256
  • 415
  • 6
    "multiple varargs" is *completely* a different issue from "varargs always last". – Ignacio Vazquez-Abrams Feb 21 '12 at 06:16
  • @Ignacio Vazquez-Abrams Other languages don't allows multiple varargs also? – Sam Feb 21 '12 at 06:24
  • 1
    They are closely related.... I'd argue that the constraint of varargs only being the last argument is what *causes* multiple varargs to be impossible. – mikera Feb 21 '12 at 06:27
  • @mikera I having accepted the your comment(yoy say:"They are closely related") but in last sample,compiler can distinguish three parameter,two last parameter are grapefruit and orang,and others are apples. – Sam Feb 21 '12 at 06:31
  • 1
    It's also possible for the compiler to just outright reject all variants which may cause ambiguities, rather than just putting it in the spec. – Ignacio Vazquez-Abrams Feb 21 '12 at 06:36
  • This can't be achieved by resolving the arguements backwards ? Anyways the runtime will know how many arguements are passed if there are 20 total then the last two are grapefruit and orange and the rest in apples. – prajeesh kumar Feb 21 '12 at 06:45
  • I don't understand why ain't your answer is accepted as the Correct Answer? – Ajay Bhojak Sep 11 '17 at 20:32