212

It looks like arraylist is not doing its job for presizing:

// presizing 

ArrayList<Integer> list = new ArrayList<Integer>(60);

Afterwards when I try to access it:

list.get(5) 

Instead of returning 0 it throws IndexOutOfBoundsException: Index 5 out of bounds for length 0.

Is there a way to initialize all elements to 0 of an exact size like what C++ does?

Daniel S.
  • 6,458
  • 4
  • 35
  • 78
Frost
  • 3,786
  • 5
  • 23
  • 29
  • 7
    The Javadoc of that constructor specifies that it creates an "empty list". It is doing its job. – ColinD Apr 08 '11 at 21:05

5 Answers5

524

The integer passed to the constructor represents its initial capacity, i.e., the number of elements it can hold before it needs to resize its internal array (and has nothing to do with the initial number of elements in the list).

To initialize an list with 60 zeros you do:

List<Integer> list = new ArrayList<Integer>(Collections.nCopies(60, 0));

If you want to create a list with 60 different objects, you could use the Stream API with a Supplier as follows:

List<Person> persons = Stream.generate(Person::new)
                             .limit(60)
                             .collect(Collectors.toList());
aioobe
  • 413,195
  • 112
  • 811
  • 826
  • 1
    That is much better than my solution (even my updated one that actually works hehehe). I would recommend not making a new `ArrayList` out of it though, and instead simply program to `List`. That's a decision left to the OP, of course. – corsiKa Apr 08 '11 at 21:14
  • 12
    The list returned by `nCopies` is immutable, so creating a new `ArrayList` is probably a good idea. – aioobe Apr 08 '11 at 21:16
  • 9
    Beware that when using the `nCopies` with a complex object the collection is not instantiated with 60 different objects, but 60 times with the same object. So only use this for primitives. – membersound Feb 26 '15 at 19:37
  • 2
    @membersound, I can think of many scenarios where `nCopies` is useful with reference types: Immutable objects such as strings, null-object patterns, enum constants, ... Anyway, I updated the answer with a solution for creating 60 different objects. – aioobe Mar 02 '15 at 18:04
  • @aioobe I know there are many scenarios where ncopies is useful. I just wanted to add this, as I tried ncopies with mutable objects and was surprised it did not work as I'd expect. Just in case anyone tries the same task. thanks for the update though! – membersound Mar 02 '15 at 21:20
13
// apparently this is broken. Whoops for me!
java.util.Collections.fill(list,new Integer(0));

// this is better
Integer[] data = new Integer[60];
Arrays.fill(data,new Integer(0));
List<Integer> list = Arrays.asList(data);
corsiKa
  • 81,495
  • 25
  • 153
  • 204
9

Java 8 implementation (List initialized with 60 zeroes):

List<Integer> list = IntStream.of(new int[60])
                    .boxed()
                    .collect(Collectors.toList());
  • new int[N] - creates an array filled with zeroes & length N
  • boxed() - each element boxed to an Integer
  • collect(Collectors.toList()) - collects elements of stream
am0wa
  • 7,724
  • 3
  • 38
  • 33
7

The 60 you're passing is just the initial capacity for internal storage. It's a hint on how big you think it might be, yet of course it's not limited by that. If you need to preset values you'll have to set them yourself, e.g.:

for (int i = 0; i < 60; i++) {
    list.add(0);
}
WhiteFang34
  • 70,765
  • 18
  • 106
  • 111
0

It's not like that. ArrayList just uses array as internal respentation. If you add more then 60 elements then underlaying array will be exapanded. How ever you can add as much elements to this array as much RAM you have.

Marcin
  • 1,429
  • 8
  • 16