← Back to Home

Collections

The Java Collections Framework (JCF) provides a unified architecture to store, manipulate, and process groups of objects efficiently. It offers ready-made data structures, standard algorithms, and common interfaces, making Java code clean, scalable, and performant. This is a must-know topic for interviews and real-world Java development.

What Is the Java Collections Framework?

  • A set of interfaces, classes, and algorithms
  • Used to store and manage groups of objects
  • Located mainly in java.util package
  • Replaces legacy data structures (Vector, Hashtable)

Why Collections Are Needed

  • Dynamic size (unlike arrays)
  • Built-in data structures (List, Set, Map)
  • High performance and optimization
  • Consistent API across data structures
  • Rich utility methods (sorting, searching, etc.)

Core Components of Collections Framework

  1. Interfaces
    Define contracts for data structures.
  2. Implementations (Classes)
    Provide concrete behavior.
  3. Algorithms
    Utility methods for searching, sorting, manipulating.

Collection Hierarchy (High-Value Interview Topic)

Iterable
   └── Collection
        ├── List
        │     ├── ArrayList
        │     ├── LinkedList
        │     └── Vector
        ├── Set
        │     ├── HashSet
        │     ├── LinkedHashSet
        │     └── TreeSet
        └── Queue
              ├── PriorityQueue
              └── Deque (ArrayDeque)

Map (separate hierarchy)
   ├── HashMap
   ├── LinkedHashMap
   ├── TreeMap
   └── Hashtable
          

Major Collection Interfaces

1️⃣ List

  • Ordered collection
  • Allows duplicates
  • Index-based access

Examples: ArrayList, LinkedList

2️⃣ Set

  • No duplicate elements
  • Unordered (mostly)

Examples: HashSet, LinkedHashSet, TreeSet

3️⃣ Queue

  • Follows FIFO (generally)
  • Used for scheduling and buffering

Examples: PriorityQueue, ArrayDeque

4️⃣ Map (Not a sub-interface of Collection)

  • Stores key–value pairs
  • Keys are unique

Examples: HashMap, LinkedHashMap, TreeMap

Collections vs Arrays

Aspect Arrays Collections
Size Fixed Dynamic
Data type Primitive + Object Objects only
Performance Faster Slight overhead
Utilities Limited Rich APIs
Flexibility Low High

Commonly Used Collection Classes

Class 특징
ArrayList Fast random access
LinkedList Fast insert/delete
HashSet No duplicates, fast lookup
TreeSet Sorted set
HashMap Fast key-value access
TreeMap Sorted map

Utility Class: Collections

Provides static methods:

  • sort()
  • reverse()
  • shuffle()
  • binarySearch()
Collections.sort(list);
          

Iterating Collections

Common ways:

  • Enhanced for-each loop
  • Iterator
  • ListIterator
for (String s : list) {
    System.out.println(s);
}
          

Key Characteristics of Collections

  • Store objects only (use wrapper classes)
  • Grow and shrink dynamically
  • Support generics for type safety
  • Designed for performance and scalability

Common Beginner Mistakes

  • Using wrong collection type
  • Ignoring time complexity
  • Forgetting generics
  • Modifying collection while iterating
  • Using legacy classes unnecessarily

Interview-Ready Answers

Short Answer

The Java Collections Framework is a set of classes and interfaces used to store and manipulate groups of objects.

Detailed Answer

The Java Collections Framework provides a unified architecture of interfaces and classes such as List, Set, Queue, and Map, enabling efficient storage, retrieval, and manipulation of data. It offers dynamic sizing, built-in algorithms, and consistent APIs.

Key Takeaway

Collections are the backbone of Java data handling. Choosing the right collection type directly impacts performance, readability, and scalability.

Hands-On Examples: Collections in Action

1. ArrayList – Allow Duplicates & Maintain Order

import java.util.*;

class Demo {
    public static void main(String[] args) {
        List<String> list = new ArrayList<>();
        list.add("Java");
        list.add("Java");
        list.add("API");
        System.out.println(list);
    }
}
          

Output

[Java, Java, API]

2. LinkedList – List + Queue Behavior

import java.util.*;

class Demo {
    public static void main(String[] args) {
        LinkedList<Integer> list = new LinkedList<>();
        list.add(10);
        list.addFirst(5);
        list.addLast(20);
        System.out.println(list);
    }
}
          

Output

[5, 10, 20]

3. Vector – Synchronized List

import java.util.*;

class Demo {
    public static void main(String[] args) {
        Vector<Integer> v = new Vector<>();
        v.add(1);
        v.add(2);
        System.out.println(v);
    }
}
          

Explanation

  • Thread-safe
  • Slower than ArrayList

4. HashSet – No Duplicates, No Order

import java.util.*;

class Demo {
    public static void main(String[] args) {
        Set<Integer> set = new HashSet<>();
        set.add(10);
        set.add(10);
        set.add(20);
        System.out.println(set);
    }
}
          

Output

[10, 20]

5. LinkedHashSet – No Duplicates, Maintains Insertion Order

import java.util.*;

class Demo {
    public static void main(String[] args) {
        Set<String> set = new LinkedHashSet<>();
        set.add("B");
        set.add("A");
        set.add("B");
        System.out.println(set);
    }
}
          

Output

[B, A]

6. TreeSet – Sorted Set

import java.util.*;

class Demo {
    public static void main(String[] args) {
        Set<Integer> set = new TreeSet<>();
        set.add(30);
        set.add(10);
        set.add(20);
        System.out.println(set);
    }
}
          

Output

[10, 20, 30]

7. HashMap – Key-Value, No Order

import java.util.*;

class Demo {
    public static void main(String[] args) {
        Map<Integer, String> map = new HashMap<>();
        map.put(1, "Java");
        map.put(2, "API");
        System.out.println(map);
    }
}
          

8. HashMap – Duplicate Key Overwrites Value

import java.util.*;

class Demo {
    public static void main(String[] args) {
        Map<Integer, String> map = new HashMap<>();
        map.put(1, "Java");
        map.put(1, "Selenium");
        System.out.println(map);
    }
}
          

Output

{1=Selenium}

9. LinkedHashMap – Maintains Insertion Order

import java.util.*;

class Demo {
    public static void main(String[] args) {
        Map<Integer, String> map = new LinkedHashMap<>();
        map.put(2, "B");
        map.put(1, "A");
        System.out.println(map);
    }
}
          

Output

{2=B, 1=A}

10. TreeMap – Sorted by Key

import java.util.*;

class Demo {
    public static void main(String[] args) {
        Map<Integer, String> map = new TreeMap<>();
        map.put(3, "C");
        map.put(1, "A");
        map.put(2, "B");
        System.out.println(map);
    }
}
          

Output

{1=A, 2=B, 3=C}

11. Iterating Collection Using for-each

import java.util.*;

class Demo {
    public static void main(String[] args) {
        List<String> list = Arrays.asList("A", "B", "C");
        for (String s : list) {
            System.out.println(s);
        }
    }
}
          

12. Iterating Using Iterator

import java.util.*;

class Demo {
    public static void main(String[] args) {
        List<Integer> list = Arrays.asList(1, 2, 3);
        Iterator<Integer> it = list.iterator();
        while (it.hasNext()) {
            System.out.println(it.next());
        }
    }
}
          

13. Removing Element Using Iterator (Safe Way)

import java.util.*;

class Demo {
    public static void main(String[] args) {
        List<Integer> list = new ArrayList<>(Arrays.asList(1, 2, 3));
        Iterator<Integer> it = list.iterator();
        while (it.hasNext()) {
            if (it.next() == 2) {
                it.remove();
            }
        }
        System.out.println(list);
    }
}
          

Output

[1, 3]

14. Collections.sort() – Natural Order

import java.util.*;

class Demo {
    public static void main(String[] args) {
        List<Integer> list = Arrays.asList(3, 1, 2);
        Collections.sort(list);
        System.out.println(list);
    }
}
          

Output

[1, 2, 3]

15. Custom Sorting Using Comparator

import java.util.*;

class Demo {
    public static void main(String[] args) {
        List<String> list = Arrays.asList("Java", "API", "Test");
        list.sort((a, b) -> a.length() - b.length());
        System.out.println(list);
    }
}
          

Output

[API, Test, Java]

16. Collections.reverse()

import java.util.*;

class Demo {
    public static void main(String[] args) {
        List<Integer> list = Arrays.asList(1, 2, 3);
        Collections.reverse(list);
        System.out.println(list);
    }
}
          

Output

[3, 2, 1]

17. Collections.synchronizedList()

import java.util.*;

class Demo {
    public static void main(String[] args) {
        List<String> list = Collections.synchronizedList(new ArrayList<>());
        list.add("ThreadSafe");
        System.out.println(list);
    }
}
          

18. Collections.unmodifiableList()

import java.util.*;

class Demo {
    public static void main(String[] args) {
        List<String> list = List.of("A", "B");
        List<String> unmodifiable = Collections.unmodifiableList(list);
        System.out.println(unmodifiable);
        // unmodifiable.add("C"); // ❌ throws exception
    }
}
          

19. Queue – PriorityQueue

import java.util.*;

class Demo {
    public static void main(String[] args) {
        Queue<Integer> q = new PriorityQueue<>();
        q.add(30);
        q.add(10);
        q.add(20);
        System.out.println(q.poll());
    }
}
          

Output

10

20. Interview Summary – Collections Framework

import java.util.*;

class Demo {
    public static void main(String[] args) {
        List<String> list = new ArrayList<>();
        Set<String> set = new HashSet<>();
        Map<Integer, String> map = new HashMap<>();

        System.out.println("Collections used");
    }
}
          

Key Points

  • List → duplicates allowed, ordered
  • Set → no duplicates
  • Map → key-value pairs
  • Hash* → fast, unordered
  • Tree* → sorted
  • LinkedHash* → insertion order