0

My question is quite simple.

Is there a method in core Java that does the following code:

<T> T[] asArray(T... values) {
    return values;
}

I tried looking for it in Arrays class, but there seems to be no such method.

To give you a context:

The previous person who worked on this code decided that varargs is better than regular array in class constructor (even though it IS supposed to be an array). Right now I have to add another generic array as the last parameter of the constructor thus transforming this code:

public Clazz(String... values) {
}

to this

public <T> Clazz(String[] values, T[] additionalParameters)

As a result I need to refactor all places where this constructor was used. What is worse that there is a couple other classes that follow the same pattern and I need to be modify them sometime in the future. And that is where above mentioned method asArray could help.

I know that it is better to just replace varargs with explicit array creation in every occurrence (and that is what I am going to do anyway), but I still want to know if there is such method already (just out of mere curiosity).

a_horse_with_no_name
  • 440,273
  • 77
  • 685
  • 758
DeGriz
  • 178
  • 1
  • 13
  • In Java 8+, you might do `return (T[]) Stream.of(values).toArray();` and in earlier version `return Arrays.asList(values).toArray(values);`. – Elliott Frisch Apr 29 '16 at 13:29
  • 1
    Note that generic array types (such as `T[]`) have [limited support](http://stackoverflow.com/q/529085/113632) and are a common source of bugs. You'd be wise to use a `List` instead. – dimo414 Apr 29 '16 at 13:30
  • Well, you could also just create your array an equal it to `T...` values. `T[] tArray = values;` – Jaims Apr 29 '16 at 13:33

2 Answers2

6

The JDK doesn't need to provide such a method since you get the same behavior by simply constructing an array - e.g.:

// these two statements are conceptually identical
String[] a = asArray("a", "b", "c");
String[] b = new String[]{"a", "b", "c"};
dimo414
  • 42,340
  • 17
  • 131
  • 218
-2

You can do:

T[] a = Stream.of(t1, t2, t3).toArray();
Jean Logeart
  • 48,718
  • 10
  • 76
  • 108
  • Yeah, that is an interesting solution. I don't know why I didn't think about it myself. :) – DeGriz Apr 29 '16 at 13:35
  • 1
    This first constructs an array (from the varargs), which is passed into a new `ArraySpliterator`, which is then passed into a new `Stream`, which then allocates a second array (in `.toArray()`), which it then copies in linear time from the original array into a new `Node` via at least one additional linear `copyInto()`, before finally returning an array. Multiple array copies and numerous object allocations, for what benefit? – dimo414 Apr 29 '16 at 14:07
  • @dimo414 On a varargs? I'd be surprised if it contains more than 10 elements! Write clean code instead of thinking of 10 elements array allocation. – Jean Logeart Apr 29 '16 at 14:21
  • 2
    You'll really want to use the overloaded `toArray` method here. In which case, you probably should've just generated the array yourself. – Sotirios Delimanolis Apr 29 '16 at 14:28
  • @JeanLogeart I'm not sure I understand your point, this *isn't* clean code. – dimo414 Apr 29 '16 at 15:27
  • @dimo414 This is clean code to me. Just not a clean problem :) – Jean Logeart Apr 29 '16 at 17:05
  • 2
    -1 again. This will a) fail to compile, because the array's of the wrong type; b) it's longer than just creating the array as in dimo's answer. – Louis Wasserman Apr 29 '16 at 18:39