Stage 4: HashMap internals, lesson 8 of 13

HashMap internals 8: Initial capacity

Intermediate3 min read@since 19Code runs on your Java 25
Explain it forThe essentials plus production detail and pitfalls.

Capacity is the number of buckets. The default is 16.

  • You can ask for more: new HashMap<>(100). HashMap rounds up to the next power of two: 10 becomes 16, 17 becomes 32, 100 becomes 128.
  • The table is created on the first put, so an empty HashMap costs almost nothing.
  • Presizing avoids repeated resizes when you know roughly how many entries are coming. The catch is that the argument is a capacity, not an entry count: new HashMap<>(1000) gets 1024 buckets but a threshold of 768, so it still resizes at entry 769.
  • Java 19 added HashMap.newHashMap(int), which takes the number of entries and does the maths for you. On older versions use new HashMap<>((int) (n / 0.75f) + 1).
HashMap lab

Example

Java
Map<String, Integer> a = new HashMap<>(100);      // 128 buckets (rounded up to a power of two)

// You expect 1000 entries:
Map<String, Integer> wrong = new HashMap<>(1000);            // 1024 buckets, threshold 768: resizes at 769
Map<String, Integer> right = HashMap.newHashMap(1000);       // Java 19+: sized so 1000 entries never resize
Map<String, Integer> older = new HashMap<>((int) (1000 / 0.75f) + 1);   // the same idea before Java 19

Common mistake

Writing new HashMap<>(n) for n expected entries and assuming it will never resize.

Under the hood

The rounding is done by a small bit-twiddling method, tableSizeFor, which finds the next power of two by smearing the highest set bit to the right. HashSet, LinkedHashMap and LinkedHashSet have the same constructor behaviour, and Java 19 added matching newHashSet, newLinkedHashMap and newLinkedHashSet factory methods.

Check yourself

What capacity does new HashMap<>(100) actually use?

How this connects

Part of HashMap internals, part by part.

Was this lesson helpful?

Finished reading? Mark it complete to track your progress.