双...在正式的参数类型声明双[]的区别 [英] Difference between double... and double[] in formal parameter type declaration

查看:187
本文介绍了双...在正式的参数类型声明双[]的区别的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我有问题:?什么是这两个声明的区别

I have question: what is the difference between these two declarations?

 public static void printMax(double... numbers) { ... }

 public static void printmax(double numbers[])  { ... }

双...号双号[]

推荐答案

键入... 构造方法中的参数声明通常是所谓的可变参数。在JLS,它被称为的可变参数数量的参数。

On varargs

The Type... construct in method parameter declaration is commonly what is called varargs. In JLS, it's called the variable arity parameter.

在列表中的最后一次正式参数是特殊的;它可能是一个的可变参数数量的参数,按照类型省略号表示。

The last formal parameter in a list is special; it may be a variable arity parameter, indicated by an elipsis following the type.

如果在最后一次正式参数的类型为 T 的可变参数数量的参数,它被认为是定义类型的形式参数 T [] 。该方法是那么的可变参数数量的方法。否则,它是一个的固定元数的方法。可变元数方法的调用可能包含更多的实际参数前pressions比形式参数。所有实际参数前$ P $不符合形式参数preceding可变参数元数将pssions进行评估,并把结果存储到将要传递给方法调用数组。

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 method is then a variable arity method. Otherwise, it is a fixed arity method. Invocations of a variable arity method may contain more actual argument expressions than formal parameters. All the actual argument expressions that do not correspond to the formal parameters preceding the variable arity parameter will be evaluated and the results stored into an array that will be passed to the method invocation.

为了说明code,这是可变参数允许你这样做:

To illustrate in code, this is what varargs allows you to do:

static void f(int... nums) {
    for (int num : nums) {
        System.out.println(num);
    }
}
//...

f(1,2,3); // prints "1", "2", "3"

在此相反,没有可变参数的构造,你必须这样做:

In contrast, without the varargs construct, you must do this:

static void g(int[] nums) {
    for (int num : nums) {
        System.out.println(num);
    }       
}
//...

g(new int[] { 1, 2, 3 }); // prints "1", "2", "3"

该可变参数是所谓的语法糖从你隐藏详细程度。

The varargs is what is called a syntactic sugar that hides the verbosity from you.

所以,回到你的问题,之间的区别一个printMax(双...数字)一个printMax(双号[])是第一个是可变参数数量的方法,这意味着你可以给它一个可变数量的参数。后者是一个的固定元数的方法,这意味着它将接受一个和唯一的参数。

So to go back to your question, the difference between printMax(double... numbers) and printmax(double numbers[]) is that the first is a variable arity method, meaning you can give it a variable number of parameters. The latter is a fixed arity method, meaning it will accept one and only parameter.

请注意上面关于 T ... 报价是一个真正的 T [] 。也就是说,即使可变参数,你仍然可以做到以下几点:

Note the quote above about T... being really a T[]. That is, even with varargs, you can still do the following:

f(new int[] { 1, 2, 3 }); // prints "1", "2", "3"

在这里,我们手动创建数组来保存可变参数的参数。事实上,如果你走得太远,因为反编译的code,你会发现,就像指定JLS,˚F是否确实需要 INT [] 参数, F(1,2,3)实现为 F(新INT [] { 1,2,3})

Here you're manually creating the array to hold the vararg parameters. In fact, if you go as far as decompiling the code, you'll find that just as JLS specified, f does in fact take int[] parameter, and f(1, 2, 3) is implemented as f(new int[] { 1, 2, 3 }).

  • Java language guide/varargs

如何可变参数都解决是相当复杂的,有时它的东西,可能会让你大吃一惊。

How varargs are resolved is quite complicated, and sometimes it does things that may surprise you.

考虑这个例子:

static void count(Object... objs) {
    System.out.println(objs.length);
}

count(null, null, null); // prints "3"
count(null, null); // prints "2"
count(null); // throws java.lang.NullPointerException!!!

由于可变参数是如何解决的,最后的语句的OBJ = NULL 调用,这当然会引起 NullPointerException异常 objs.length 。如果你想举一个参数可变参数一个参数,您可以执行以下操作:

Due to how varargs are resolved, the last statement invokes with objs = null, which of course would cause NullPointerException with objs.length. If you want to give one null argument to a varargs parameter, you can do either of the following:

count(new Object[] { null }); // prints "1"
count((Object) null); // prints "1"

相关问题

下面是一些与可变参数打交道时,人们已经提出的问题的例子:

Related questions

The following is a sample of some of the questions people have asked when dealing with varargs:

  • bug with varargs and overloading?
  • How to work with varargs and reflection
  • Most specific method with matches of both fixed/variable arity (varargs)

由于previous切片显示,可变参数可能会非常棘手。用于在正确的情况下,但是,它们可以导致更加简洁code。

As the previous section showed, varargs can be tricky. Used in the right situations, however, they can lead to much more concise code.

下面是一个引自的有效的Java第二版,项目42:使用可变参数明智的(按作者强调):

Here's a quote from Effective Java 2nd Edition, Item 42: Use varargs judiciously (emphasis by author):

教训是明显的。 不要每次改造具有最终数组参数的方法;使用可变参数的只有的当呼叫真正运行在值的可变长度序列

The lesson is clear. Don't retrofit every method that has a final array parameter; use varargs only when a call really operates on a variable-length sequence of values.

不仅可以可变参数是混乱的,它也可能是昂贵的。的有效的Java第二版的建议实际上是最常见的使用场景提供固定元数的重载。

Not only can varargs be confusing, it can also be costly. Effective Java 2nd Edition actually recommends providing fixed-arity overloads for the most common usage scenarios.

假设你已经确定了95%的呼叫的方法有三个或更少的参数。然后声明该方法五个overloadings,每个零通过三个普通的参数,以及一个单一的可变参数时使用的参数的数目超过3个

Suppose you've determined that 95 percent of the calls to a method have three or fewer parameters. Then declare five overloadings of the method, one for each with zero through three ordinary parameters, and a single varargs for use when the number of parameters exceed three.

这本书去更加深入,但本质上你应该只使用可变参数时,它实际上是有意义的。即使在这种情况下,你可能仍然要考虑性能方面的原因提供固定元数的重载。

The book goes in much greater depth, but essentially you should only use varargs when it actually makes sense. And even in those cases, you may still want to consider providing fixed-arity overloads for performance reasons.

  • Java’s varargs performance.

下面是一些例子,其中可变参数是有道理的:

Here are some examples where varargs makes sense:

请,请,不作声明数组这样的习惯:

Please, please, do not make a habit of declaring arrays like this:

int x[];

您应该改为放支架用的键入的,而不是用的标识的:

You should instead put the brackets with the type, rather than with the identifier:

int[] x;

请注意,这也是阵列如何在上述的讨论中,例如称为 T [] INT []

Note that this is also how arrays are referred to in the above discussions, e.g. T[] int[], etc.

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆