the intended best usage for the "Collection.toArray(T[] destination)" method. Is it better to create destination array of correct size ourselves and pass it? Or is it better to create a zero-sized throw away array just to pass type info so jdk can create it itself?
I'm adding a screenshot to demonstrate the IDE warn, not the code itself (admins, please don't delete it). So for some reason Intellij IDEA considers this as a code smell.
However when I check the documentation (is in screenshot), and explore the jdk implementation of this method, I clearly see that it's designed to be used both ways.
Here's how "toArray" is implemented, it clearly matches the javadoc:
public <T> T[] toArray(T[] a) {
// Estimate size of array; be prepared to see more or fewer elements
int size = size();
T[] r = a.length >= size ? a : ...<create new array>;
// iterate and copy elements to "r"
... }
screenshots are fine, it's photos of screen that we have problems with :)
just a curiosity, why?
Collection.toArray() actually creates an array containing all the elements of the collection. You don't have to specify a size there. May be, that's the code smell it's pointing out.
because it's lazy and they aren't legible most of the time. We can't ban use of screenshots since it is required sometimes to explain things, like UI problems And if one can't be bothered to explain their problem properly they shouldn't expect others to bother with their problems. Also enabling this laziness comes back to drain us in the form of help vampires
But "Collection.toArray()" (no args) creates untyped generic "Object[]" array. We always lose type information when using this method. This is different. My question is about other method - "Collection.toArray(T[] array)". Assume that I need convert collection of strings (Collection<String>) to array of strings (String[]). Not to array of objects. Well, actually my example with mongoTemplate is not very clearly explains the question as mongoTemplate expectes Object[] ))) Ok, let me be more precise. IDE suggests me to - not use myStringsCollection.toArray(new String[myStrings.size()]) - but instead use myStringsCollection.toArray(new String[0]) And it shows that strange Call to 'toArray()' with pre-sized array argument 'new String[globalIds.size()]' warning. So my question is: why toArray with pre-prepared destination array may be a code smell? Why it's better to use toArray(new String[0]) instead according to IDE?
Interesting topic indeed. I think in the end it just comes down to speed. Zero is faster than sized. If you want to know what is really going on, it‘s time for some reading :p Have fun. It‘s a wild ride... but totally worth it imho: https://shipilev.net/blog/2016/arrays-wisdom-ancients/
Weird if it's all about the speed. In jdk that I'm using (azul 11.0.9), zero-length will end up with calling this reflections stuff, which I highly doubt that can be faster: T[] r = a.length >= size ? a : (T[])java.lang.reflect.Array .newInstance(a.getClass().getComponentType(), size); Thank you for article! Shipilev is great engineer, and I'm 100% sure the article worth every minute spent reading it
The article is great yeah :) Hmm I guess you‘d have to check it with a profiler in a similar way as described in the article, to find out more.
I finally got to the article. Reading it now. Super-duper weird, but screenshot of Intellij IDEA 15 in the article shows the opposite IDE suggestion: IDEA suggests to NOT use .toArray(new Foo[0]), whereas my IDEA (built on Apr 06, 2011) shows the opposite - it suggests me to replace globalIds.toArray(new Object[globalIds.size()]) with globalIds.toArray(new Object[0]). Weird Interesting..... continue reading. I did not expect this question to be so complex)))
Обсуждают сегодня