LinkedHashSet in Java – Preserving Insertion Order

Illustration for LinkedHashSet in Java – Preserving Insertion Order
By Last updated:

LinkedHashSet is a unique Set implementation in Java that combines hashing performance with predictable iteration order. It maintains a doubly-linked list across all entries, preserving the insertion order of elements.

In this tutorial, you’ll learn how LinkedHashSet works internally, its performance profile, use cases, common pitfalls, and how it compares with HashSet and TreeSet.


🧠 What is LinkedHashSet?

  • Implements Set interface
  • Extends HashSet
  • Maintains insertion order
  • Does not allow duplicates
  • Not thread-safe
Set<String> set = new LinkedHashSet<>();
set.add("Banana");
set.add("Apple");
set.add("Banana"); // Duplicate ignored
System.out.println(set); // [Banana, Apple]

🛠️ Internal Working: HashMap + Linked List

Internally, LinkedHashSet uses a LinkedHashMap, which itself extends HashMap and adds a doubly-linked list to maintain order.

private transient LinkedHashMap<E,Object> map;
private static final Object PRESENT = new Object();

How It Works:

  • Keys are stored in a HashMap for O(1) lookup
  • A doubly-linked list maintains order across the keys

When you call set.add("Java"), it internally does:

map.put("Java", PRESENT);

🧩 Insertion Order Guarantee

Unlike HashSet, iteration order in LinkedHashSet is the same as the order in which elements were inserted.

Set<String> ordered = new LinkedHashSet<>();
ordered.add("C");
ordered.add("A");
ordered.add("B");
System.out.println(ordered); // [C, A, B]

⏱️ Performance Benchmarks

Operation Time Complexity Notes
add() O(1) average Same as HashSet
remove() O(1) average Maintains linked pointers
contains() O(1) average Via HashMap lookup
iterator() O(n) Preserves insertion order

✅ Real-World Use Cases

  • Order-preserving de-duplication
  • Caching mechanisms (least recently used)
  • Maintaining history or sequence-sensitive sets
  • Preserving user preferences or navigation trails
List<String> raw = List.of("b", "a", "c", "a");
Set<String> uniqueOrdered = new LinkedHashSet<>(raw);
System.out.println(uniqueOrdered); // [b, a, c]

🔁 LinkedHashSet vs HashSet vs TreeSet

Feature HashSet LinkedHashSet TreeSet
Order ❌ No order ✅ Insertion ✅ Sorted
Performance ✅ Fast ✅ Fast ❌ Slower
Null Support ✅ One null ✅ One null ❌ Risky/null
Backed By HashMap LinkedHashMap TreeMap
Sorted?

🧬 Java Streams with LinkedHashSet

List<String> names = List.of("z", "y", "x", "z");

Set<String> ordered = names.stream()
    .collect(Collectors.toCollection(LinkedHashSet::new));
System.out.println(ordered); // [z, y, x]

❌ Common Mistakes and Anti-Patterns

  • ❌ Expecting sorted output (use TreeSet instead)
  • ❌ Using LinkedHashSet for concurrent code
  • ❌ Not overriding equals() and hashCode() in custom objects

✅ Always override equals() and hashCode() for custom types used as keys.


📌 What's New in Java Versions?

Java 8

  • Stream API, Collectors.toCollection(), forEach()

Java 9

  • Immutable sets with Set.of(...)

Java 10

  • var support for cleaner syntax

Java 11

  • Minor enhancements to iteration and GC

Java 17 & 21

  • Internal optimizations, compact memory usage in collections

🔧 Refactoring Example

Before:

Set<String> dedup = new HashSet<>();
dedup.add("X");
dedup.add("Y");
dedup.add("X");
System.out.println(dedup); // Unordered

After (ordered):

Set<String> dedup = new LinkedHashSet<>();
dedup.add("X");
dedup.add("Y");
System.out.println(dedup); // [X, Y]

🧠 Real-World Analogy

Imagine a guest sign-in sheet. Every person signs in once (no duplicates), and the order is preserved forever. That’s LinkedHashSet — no repeat names, but memory of arrival order.


❓ FAQ – Expert-Level Questions

  1. Can LinkedHashSet contain null?

    • Yes, but only one null element.
  2. How is LinkedHashSet ordered?

    • Maintains insertion order via linked list.
  3. Is LinkedHashSet synchronized?

    • No. Wrap with Collections.synchronizedSet() if needed.
  4. Can LinkedHashSet be sorted?

    • Not natively. Use TreeSet or sort after collection.
  5. Is LinkedHashSet thread-safe?

    • No, it's not safe for concurrent modification.
  6. Can I convert LinkedHashSet to List?

    List<String> list = new ArrayList<>(linkedHashSet);
    
  7. How does iteration differ from HashSet?

    • Predictable and ordered in LinkedHashSet
  8. How does LinkedHashSet detect duplicates?

    • Uses equals() and hashCode()
  9. What is the default initial capacity and load factor?

    • 16 and 0.75 (inherited from HashMap)
  10. Is LinkedHashSet suitable for caching?

    • Yes, particularly LRU-style structures

🏁 Conclusion and Key Takeaways

  • LinkedHashSet combines the speed of HashSet with predictable ordering
  • Ideal when you need de-duplication and order preservation
  • Internally backed by LinkedHashMap
  • Best suited for scenarios like caching, history tracking, or stream de-duplication with order

🔍 Pro Tip: If order matters, LinkedHashSet is your default Set choice over HashSet.