With a varargs method, is it possible to determine if an object should be passed inline?

Zephyr :

I am working with the Apache Commons CSV library specifically, but this is a more general question.

Is it possible to skip an argument based on a condition when calling a varargs method?

Consider the following example:

class Test {
    public static void main(String[] args) {

        String str1 = "One";
        String str2 = "Two";
        String str3 = "Three";
        String str4 = "Four";
        String str5 = "Five";

        boolean excludeOne = false;
        boolean excludeTwo = false;
        boolean excludeThree = true;
        boolean excludeFour = false;
        boolean excludeFive = false;

        print(
                str1,
                str2,
                str3, // Can I skip this argument if excludeThree = true?
                str4,
                str5
        );

    }

    private static void print(Object... items) {

        for (Object item : items) {
            System.out.println(item);
        }
    }
}

My Use Case: I am working to export a TableView to CSV, but depending on certain factors, one of more columns may or may not need to be included in that output. So I need a way to determine, at runtime, if that column should be included when calling the CSVPrinter.printRecord(Object... values) method.

I know I could build a list of valid items first and pass that to the method:

List<String> filteredList = new ArrayList<>();
if (!excludeOne) filteredList.add(str1);
if (!excludeTwo) filteredList.add(str2);
if (!excludeThree) filteredList.add(str3);
if (!excludeFour) filteredList.add(str4);
if (!excludeFive) filteredList.add(str5);

print(filteredList.toArray());

Just wondering if there is a shorter, in-line way of determining the arguments.

Daniel Pryden :

No, there is no syntax to change the length of a varargs array based on a runtime condition. If the length of the array is only determined at runtime, it must be passed as a single array argument (like your filteredList.toArray() example).

Reference: Java Language Specification 15.12.4.2 says:

If m is being invoked with k ≠ n actual argument expressions [...], then the argument list (e1, ..., en-1, en, ..., ek) is evaluated as if it were written as (e1, ..., en-1, new |T[]| { en, ..., ek }), where |T[]| denotes the erasure (§4.6) of T[].

The argument expressions (possibly rewritten as described above) are now evaluated to yield argument values. Each argument value corresponds to exactly one of the method's n formal parameters.

In your case, this means that if you have five actual argument expressions in your function call, the function will always receive an Object[] array with exactly five elements. You can't have any more or any less: the number of elements in the array is determined at compile time.

Guess you like

Origin http://43.154.161.224:23101/article/api/json?id=130225&siteId=1