3.4 Java Data Structures 101: Collections You'll Use Every Day
If you’re new to Java, this part can feel overwhelming fast.
You open a codebase and see ArrayList, HashMap, TreeMap, HashSet,
ArrayDeque, and you think, “Cool… but which one do I use right now?”
That’s exactly what this guide fixes.
We’re going to cover the data structures you will use constantly in beginner projects, coding interviews, and real jobs.
Quick Truth
You don’t need to memorize every collection in Java. You need to understand the common ones deeply enough to pick the right tool for the job.
First, the Mental Model
Think of Java collections like different kinds of storage containers:
- Need a numbered list? Use
List - Need fast lookup by key? Use
Map - Need unique values only? Use
Set - Need first-in-first-out or stack-like behavior? Use
QueueorDeque
One important detail: Map is part of the Java Collections Framework, but it
does not extend the Collection interface.
The 80/20 Rule: Start with These
If you only learn these six really well, you’re in great shape:
ArrayListHashMapTreeMapHashSetTreeSetArrayDeque
We’ll also touch LinkedList and PriorityQueue because you will see them.
Super Fast Decision Guide
- Use
ArrayListwhen you want an ordered list and frequent reads - Use
HashMapwhen you want key-value lookups and speed - Use
TreeMapwhen you want key-value data sorted by key - Use
HashSetwhen you need uniqueness and don’t care about order - Use
TreeSetwhen you need uniqueness plus sorted order - Use
ArrayDequefor queue/stack behavior
If you’re unsure, default to ArrayList or HashMap. That’s what most code
starts with.
1) ArrayList: Your Default List
ArrayList is usually your go-to list implementation.
Why developers love it
- Keeps insertion order
- Fast random access by index
- Great for iterating
- Simple and predictable
ArrayList Example
1import java.util.ArrayList;
2import java.util.List;
3
4public class ArrayListExample {
5 public static void main(String[] args) {
6 List<String> tasks = new ArrayList<>();
7 tasks.add("Review pull request");
8 tasks.add("Fix failing test");
9 tasks.add("Deploy to staging");
10
11 String firstTask = tasks.get(0);
12 tasks.remove("Fix failing test");
13
14 System.out.println(firstTask);
15 System.out.println(tasks);
16 }
17}ArrayList Watch-out
Inserting or removing from the middle of a large ArrayList can be expensive
because elements may shift.
2) HashMap: Fast Key-Value Lookup
Need to look up data by a key fast? HashMap is your friend.
Great for
- Counting things
- Caching
- User/profile lookup by ID
- Grouping data by category
HashMap Example
1import java.util.HashMap;
2import java.util.Map;
3
4public class HashMapExample {
5 public static void main(String[] args) {
6 Map<String, Integer> ticketsByStatus = new HashMap<>();
7 ticketsByStatus.put("open", 12);
8 ticketsByStatus.put("in_progress", 7);
9 ticketsByStatus.put("done", 23);
10
11 int openTickets = ticketsByStatus.getOrDefault("open", 0);
12 ticketsByStatus.merge("open", 1, Integer::sum);
13
14 System.out.println(openTickets);
15 System.out.println(ticketsByStatus);
16 }
17}HashMap Watch-out
- Iteration order is not guaranteed
nullkeys and values are allowed, but use them carefully
3) TreeMap: Sorted Map by Key
TreeMap keeps keys sorted automatically.
If you need “show results in key order” without sorting later, this is a solid choice.
TreeMap Example
1import java.util.Map;
2import java.util.TreeMap;
3
4public class TreeMapExample {
5 public static void main(String[] args) {
6 Map<Integer, String> leaderboard = new TreeMap<>();
7 leaderboard.put(200, "Kai");
8 leaderboard.put(120, "Riley");
9 leaderboard.put(340, "Jordan");
10
11 System.out.println(leaderboard);
12 }
13}TreeMap Watch-out
TreeMap is typically slower than HashMap for basic insert/get operations,
but gives you sorted keys in return.
4) HashSet: Unique Values, Fast Membership Checks
Use HashSet when duplicates are not allowed.
HashSet Example
1import java.util.HashSet;
2import java.util.Set;
3
4public class HashSetExample {
5 public static void main(String[] args) {
6 Set<String> tags = new HashSet<>();
7 tags.add("java");
8 tags.add("backend");
9 tags.add("java");
10
11 System.out.println(tags.contains("java"));
12 System.out.println(tags.size());
13 }
14}HashSet Watch-out
No guaranteed iteration order.
5) TreeSet: Unique + Sorted
Need uniqueness and sorted output? Use TreeSet.
TreeSet Example
1import java.util.Set;
2import java.util.TreeSet;
3
4public class TreeSetExample {
5 public static void main(String[] args) {
6 Set<String> skills = new TreeSet<>();
7 skills.add("spring");
8 skills.add("java");
9 skills.add("docker");
10
11 System.out.println(skills);
12 }
13}6) ArrayDeque: Better Queue/Stack Default
For queue or stack behavior, ArrayDeque is often the best general-purpose
choice.
Queue-style example
1import java.util.ArrayDeque;
2import java.util.Deque;
3
4public class ArrayDequeExample {
5 public static void main(String[] args) {
6 Deque<String> queue = new ArrayDeque<>();
7 queue.offer("job-1");
8 queue.offer("job-2");
9 queue.offer("job-3");
10
11 String next = queue.poll();
12 System.out.println(next);
13 System.out.println(queue);
14 }
15}Two More You Should Recognize
LinkedList
LinkedList implements both List and Deque. It’s useful in some specific
cases, but most beginner code is better with ArrayList or ArrayDeque.
PriorityQueue
PriorityQueue processes elements by priority instead of insertion order.
Great for scheduling and “next best” style problems.
1import java.util.PriorityQueue;
2import java.util.Queue;
3
4public class PriorityQueueExample {
5 public static void main(String[] args) {
6 Queue<Integer> priorities = new PriorityQueue<>();
7 priorities.offer(30);
8 priorities.offer(10);
9 priorities.offer(20);
10
11 System.out.println(priorities.poll());
12 }
13}Common Beginner Mistakes
1) Picking concrete types everywhere
Prefer interface types in your variable declarations:
1import java.util.ArrayList;
2import java.util.List;
3
4public class InterfaceTypeExample {
5 public static void main(String[] args) {
6 List<String> names = new ArrayList<>();
7 names.add("Ari");
8 System.out.println(names);
9 }
10}This makes your code easier to change later.
2) Forgetting equals() and hashCode() for custom objects
If you use your own class in HashSet or as keys in HashMap, define
equals() and hashCode() properly, or behavior may look broken.
3) Ignoring ordering requirements
If order matters, choose a structure that guarantees the order you need.
Don’t assume HashMap or HashSet will keep insertion order.
Real-World Mini Example
You can combine structures in one workflow:
ArrayListfor raw events in arrival orderHashMapto count events by typeTreeMapto produce sorted reporting output
1import java.util.ArrayList;
2import java.util.HashMap;
3import java.util.List;
4import java.util.Map;
5import java.util.TreeMap;
6
7public class EventPipelineExample {
8 public static void main(String[] args) {
9 List<String> events = new ArrayList<>();
10 events.add("login");
11 events.add("purchase");
12 events.add("login");
13
14 Map<String, Integer> counts = new HashMap<>();
15 for (String event : events) {
16 counts.merge(event, 1, Integer::sum);
17 }
18
19 Map<String, Integer> sortedCounts = new TreeMap<>(counts);
20 System.out.println(sortedCounts);
21 }
22}That pattern shows up everywhere in data processing and backend services.
Quick Performance Intuition
You don’t need to memorize every complexity table right now. Just remember:
ArrayList: fast reads by index, slower middle insert/deleteHashMap/HashSet: usually very fast lookupTreeMap/TreeSet: sorted behavior with extra overheadArrayDeque: fast queue/stack operations
This is enough to make good decisions as a beginner.
What to Practice This Week
- Build a small contact manager with
ArrayList - Add ID-based lookup with
HashMap - Produce alphabetical output with
TreeMap - Track unique tags with
HashSet - Add a simple task queue with
ArrayDeque
Final Takeaway
Here’s the big idea: Java collections are not about memorizing everything.
They’re about choosing the right container for the job.
Start with ArrayList and HashMap. Add TreeMap, HashSet, and
ArrayDeque as your projects grow. Keep it simple, then get fancy when you
actually need to.
You’re not behind. You’re learning the same toolkit professional Java developers use every day.