JavaRush /Java 博客 /Random-ZH /Java 可变参数

Java 可变参数

已在 Random-ZH 群组中发布
今天我们将讨论 Java 中的 varargs 这样的东西。Varargs(或可变参数)是一种允许您创建具有任意数量参数的方法的技术。在本文中,我们将学习如何创建此类方法,讨论为什么需要可变参数以及何时最好使用它们。

什么是可变参数?

Varargs 是可变长度参数:JDK5 中出现的一个功能。可变参数允许我们创建具有任意数量参数的方法。总的来说,以前可以创建这样的方法。确实,这样做并不是很方便。让我们举个例子。假设我们需要编写一个方法,该方法将采用任意数量的整数参数并将它们加在一起。 Java 可变参数 - 1我们有两个选择。 选项 1 - 过载:
class Calculator {
    int sum(int a, int b){...};
    int sum(int a, int b, int c){...};
    int sum(int a, int b, int c, int d){...};
    int sum(int a, int b, int c, int d, int e){...};
}
但超载有两个问题。首先,并不总是清楚什么时候该停止,其次,这很麻烦。数组更好。 选项 2 - 数组:
class Calculator {
    int sum(int[] numbers){...};
}
有了数组就不再麻烦了,而且数组看起来好像没什么……直到调用方法的时候:
public static void main(String... sss) {
    Calculator calculator = new Calculator();

    int[] arguments = new int[7];
    arguments[0] = 1;
    arguments[1] = 10;
    arguments[2] = 123;
    arguments[3] = 234;
    arguments[4] = 6234;
    arguments[5] = 12;
    arguments[6] = 8;

    int sum = calculator.sum(arguments);
}
我们同意,当然,您可以更简短地写下所有内容。但首先,我仍然想证明使用数组作为可变长度参数的不便,其次,即使我们这样写:
int[] arguments = {1,10,123,234,6234,12,8};
int sum = calculator.sum(arguments);
那么我们仍然无法摆脱过多的代码。然而,随着Java 5的发布,Varargs特性的出现解决了这些问题。它使得向方法传递任意数量的参数成为可能。它看起来像这样:
public class Calculator {
    public static void main(String... sss) {
        Calculator calculator = new Calculator();
        int sum = calculator.sum(1,10,123,234,6234,12,8);
    }
    int sum(int... numbers){
       return Arrays.stream(numbers).sum();
    }
}
那么,我们来总结一下。Varargs 是可变长度参数,这是 Java 5 发布时出现的一项功能。接下来,我们将仔细研究使用 Varargs 的一些规则。

5 条可变参数规则

规则 1. Vararg 参数(或可变/任意长度参数)由省略号指示,如下所示:
String... words
Integer... numbers
Person... people
Cat... cats
规则 2.任意长度的参数只能指定为某个方法的参数:
void print(String... words)
int sum(Integer... numbers)
void save(Person... people)
void feed(Cat... cats)
规则 3.方法主体中的每个此类可变长度参数都是一个数组:
void print(String... words){
    for (int i = 0; i < words.length; i++) {
        System.out.println(words[i]);
    }
}
规则 4. Vararg 参数必须是方法参数列表中的最后一个:
void print(String... words, String anotherWord) // - Так нельзя!
void print(String... words, int someNumber) // - Так нельзя!

void print(String anotherWord, String... words) // - Так можно
void print(int someNumber, String... words) // - Так можно
规则 5:尽管 varargs 是数组,但在调用采用可变长度参数的方法时,无需创建数组。简单地列出用逗号分隔的所需参数就足够了,甚至是可取的:
public class Main {
    public static void main(String... sss) {
        print("How","же","прекрасно","изучать","Java");
    }

    static void print(String... words){
        for (int i = 0; i < words.length; i++) {
            System.out.println(words[i]);
        }
    }
}

可变参数的示例

在下面的示例中,我们将编写一个方法,该方法采用由整数组成的可变参数并显示传递的元素数量及其总和。让我们将数组和一系列整数传递给此方法(两个选项都有效):
public static void main(String... sss) {
    int[] a = new int[100];
    for (int i = 0; i < a.length; i++) {
        a[i] = i;
    }

    sum(a);
    sum(1,2,3,4,5,6,7,8,9,10);
}

static void sum(int... numbers){
    final int length = numbers.length;
    final int sum = Arrays.stream(numbers).sum();
    final String lineSeparator = System.lineSeparator();

    System.out.printf("Кол-во элементов для сложения - %d, сумма - %d%s", length, sum, lineSeparator);
}
程序运行后会输出:

Кол-во элементов для сложения - 100, сумма - 4950 
Кол-во элементов для сложения - 10, сумма - 55 
值得一提的是,该方法System.out.printf还接受可变参数。如果我们查看这个方法的代码,我们会看到:
public PrintStream printf(String format, Object ... args) {
    return format(format, args);
}
另一种广泛使用的接受 varags 的方法是String.format. 其代码如下所示:
public static String format(String format, Object... args) {
    return new Formatter().format(format, args).toString();
}

何时使用可变参数?

这个问题的答案取决于提出问题的人。如果某个具有可变参数方法的 API 的客户端提出类似的问题,那么答案将是“尽可能频繁地使用此类方法”。对于代码客户端来说,可变参数使代码更容易编写、更具可读性,从而使生活变得更加轻松。但是,如果 API 开发人员问这个问题,并且想知道应该多久使用 varargs 创建方法,那么答案将是“您不应该经常使用 varargs”。仅当使用 Varargs 的好处显而易见时才应使用它。您还应该避免使用可变参数重载方法,因为这将使代码的客户端很难理解实际调用了哪个重载方法。

结论

所以,我们讨论了另一个主题,Java 中的可变参数。我们知道它是什么了。我们描述了使用可变参数的规则。我们研究了具有任意长度参数的方法的示例,并讨论了何时最好使用可变参数以及何时最好避免使用它们。作为作业,您可以实施以下方法:
  • 编写void一个方法,该方法接受一系列整数并返回它们的算术平均值。
  • 编写void一个方法,接受一系列字符串并打印最长的单词。
  • 编写一个方法,返回boolean并接受一个类型变量作为第一个参数String,一系列boolean变量长度作为下一个参数。
    可能的String值为AND, OR, XOR。如果第一个参数具有其他值,则该方法必须抛出异常IllegalArgumentException
    该方法必须对 varargs 参数的每个元素执行逻辑运算(在第一个参数中指定)并返回计算结果。
示例参数和结果:
  • "AND", true, true, false - 将返回 false
  • “OR”, false, true, false, false - 将返回 true
评论
TO VIEW ALL COMMENTS OR TO MAKE A COMMENT,
GO TO FULL VERSION