Inside the Dynamic Array

Underneath, a dynamic array is still built on a plain fixed-size array. We cannot avoid that, because a fixed-size array is the only storage Java gives us. We can choose a reasonable size as the initial capacity, and keep a counter of how many of the array slots hold real elements. So our class needs two fields:

public class DynamicArray {
  private int[] arr;   // the underlying fixed-size storage
  private int size;    // how many elements we've added so far
}

These two numbers are not the same thing:

  • arr.length is the capacity: how many slots the storage currently has.
  • size is the logical size: how many of those slots are actually in use.

Capacity is always at least as large as size, and usually larger. The slots from index size up to arr.length - 1 are allocated but unused.

The client only ever sees size. The capacity is internal to the class. That is the interface-and-implementation split from the previous section: size belongs to the interface, and arr.length belongs to the implementation.

The constructor

When we create a dynamic array, we do not know how many elements the client will add. So we allocate a small amount of storage to start with, and record that nothing has been added yet:

public DynamicArray() {
  arr = new int[10];  // start with room for 10 elements
  size = 0;           // but the array is logically empty
}

We have ten slots available, but zero elements. From the client’s point of view, a freshly created dynamic array has size 0.

Ten is an arbitrary choice. Any small number would do, and the class works the same way whichever one we pick, because we are going to allocate more storage once all the slots are in use.

Reporting the size

public int size() {
  return size;
}

Notice that both the field and the method are called size. Java allows this, and it can resolve each use correctly: when you mean the method rather than the variable, you add parentheses, as in size(). If you prefer, you can use a different name for the field, like count or numElements. Or you could rename the operation to involve a verb, like getSize().

Next we implement add, and then we deal with what happens once those ten slots are used up.