PYnative

Python Programming

  • Learn Python ▼
    • Python Tutorials
    • Python Basics
    • Python Interview Q&As
  • Exercises ▼
    • Python Exercises
    • C++ Exercises
    • C Programming Exercises
    • Java Exercises
    • C# Exercises
  • Quizzes
  • Online Compilers▼
    • Online Python Code Editor
    • Online C Compiler
    • Online C++ Compiler
    • Online Java Compiler
    • Online C# Compiler
Home » Java Exercises » Java ArrayList Exercises: 30 Coding Problems with Solutions

Java ArrayList Exercises: 30 Coding Problems with Solutions

Updated on: July 6, 2026 | Leave a Comment

This collection of 30 Java ArrayList exercises covers the full lifecycle of working with a list: creating and iterating, inserting and removing, searching and sorting, and combining or splitting lists.

  • Early exercises cover the three main iteration styles, indexed insertion and removal, safe retrieval with exception handling, and sorting in both ascending and descending order.
  • The middle set covers copying, shuffling, manual reversal, sublists, array conversion in both directions.
  • The final exercises tackle more advanced problems: deduplication with and without a Set, finding common elements, a frequency counter, splitting a list by condition, merging two sorted lists, the sliding window technique, and sorting custom objects with a Comparator.

Each exercise includes a Problem Statement, Purpose, Hint, and a Solution with Explanation, with an alternative approach noted wherever a more modern or concise option exists.

  • Also, See: Java Exercises with over 20+ topic-wise sets and 575+ coding questions to practice.
  • Practice questions using our Online Java Compiler
+ Table of Contents (30 Exercises)

Table of contents

  • Exercise 1: Creation and Initialization
  • Exercise 2: Iterating Elements
  • Exercise 3: Insert at First Position
  • Exercise 4: Retrieve an Element
  • Exercise 5: Update an Element
  • Exercise 6: Remove an Element
  • Exercise 7: Search for an Element
  • Exercise 8: Check for Empty List
  • Exercise 9: Sort Elements
  • Exercise 10: Copy an ArrayList
  • Exercise 11: Shuffle a List
  • Exercise 12: Reverse Elements Manually
  • Exercise 13: Extract a Sublist
  • Exercise 14: Swap Two Elements
  • Exercise 15: Join Two Lists
  • Exercise 16: Clone an ArrayList
  • Exercise 17: Array to ArrayList Conversion
  • Exercise 18: ArrayList to Array Conversion
  • Exercise 19: Replace Elements Conditionally
  • Exercise 20: Filter Even Numbers
  • Exercise 21: Trim Capacity
  • Exercise 22: Compare Two Lists
  • Exercise 23: Remove Duplicates (With Set)
  • Exercise 24: Remove Duplicates (Without Set)
  • Exercise 25: Find Common Elements
  • Exercise 26: Frequency Counter
  • Exercise 27: Split an ArrayList
  • Exercise 28: Merge Sorted Lists
  • Exercise 29: Find Continuous Sublist Sum
  • Exercise 30: Custom Object Sorting

Exercise 1: Creation and Initialization

Problem Statement: Create an ArrayList of Strings, add five names of your favorite programming languages, and print the entire list to the console.

Purpose: This exercise helps you practice basic ArrayList creation and the add() method, foundational for working with dynamic, resizable collections in Java.

Given Input: Add “Java”, “Python”, “JavaScript”, “C++”, and “Go” to a new ArrayList<String>.

Expected Output: Languages = [Java, Python, JavaScript, C++, Go]

▼ Hint
  • Import java.util.ArrayList before using the class.
  • Declare the list using ArrayList<String> and instantiate it with new ArrayList<>().
  • Use the add() method to append each language one at a time.
  • Print the entire list directly; Java’s ArrayList already provides a readable toString() format.
▼ Solution & Explanation
import java.util.ArrayList;

public class Main {
    public static void main(String[] args) {
        ArrayList<String> languages = new ArrayList<>();
        languages.add("Java");
        languages.add("Python");
        languages.add("JavaScript");
        languages.add("C++");
        languages.add("Go");

        System.out.println("Languages = " + languages);
    }
}Code language: Java (java)

Explanation:

  • new ArrayList<>(): Creates an empty, resizable list that can grow as elements are added, unlike a fixed-size array.
  • languages.add("Java"): Appends each element to the end of the list, one call per language.
  • System.out.println("Languages = " + languages): Relies on ArrayList‘s built-in toString() method, which automatically formats the list as comma-separated values inside square brackets.
  • Alternative: You could use List.of("Java", "Python", ...) combined with new ArrayList<>(...) to initialize the list in a single line, though it creates an intermediate immutable list first.

Exercise 2: Iterating Elements

Problem Statement: Write a program to iterate through all elements in an ArrayList using three different methods: a standard for loop, an enhanced for-each loop, and an Iterator.

Purpose: This exercise helps you practice the three most common iteration patterns in Java, and understand when each one is useful.

Given Input: fruits = {"Apple", "Banana", "Cherry"}

Expected Output:

Standard for: Apple Banana Cherry
For-each: Apple Banana Cherry
Iterator: Apple Banana Cherry
▼ Hint
  • For the standard for loop, use get(i) alongside size() to access elements by index.
  • For the for-each loop, iterate directly over the list without needing an index variable.
  • For the Iterator, call iterator() on the list, then use hasNext() and next() inside a while loop.
  • Print each element as you go so you can compare the output of all three approaches.
▼ Solution & Explanation
import java.util.ArrayList;
import java.util.Iterator;

public class Main {
    public static void main(String[] args) {
        ArrayList<String> fruits = new ArrayList<>();
        fruits.add("Apple");
        fruits.add("Banana");
        fruits.add("Cherry");
        System.out.print("Standard for: ");
        for (int i = 0; i < fruits.size(); i++) {
            System.out.print(fruits.get(i) + " ");
        }
        System.out.println();
        System.out.print("For-each: ");
        for (String fruit : fruits) {
            System.out.print(fruit + " ");
        }
        System.out.println();
        System.out.print("Iterator: ");
        Iterator<String> it = fruits.iterator();
        while (it.hasNext()) {
            System.out.print(it.next() + " ");
        }
        System.out.println();
    }
}Code language: Java (java)

Explanation:

  • for (int i = 0; i < fruits.size(); i++): Uses an index to access elements directly with get(i), giving full control over the position being read.
  • for (String fruit : fruits): Iterates over each element automatically without managing an index, making the code more concise for simple traversal.
  • Iterator<String> it = fruits.iterator(): Creates an explicit iterator object, useful when you need to remove elements safely during iteration with it.remove().
  • Alternative: You could use fruits.forEach(fruit -> System.out.print(fruit + " ")) with a lambda expression for a fourth, more modern iteration style.

Exercise 3: Insert at First Position

Problem Statement: Create an ArrayList of integers, add a few elements, and then insert a new integer at the first position (index 0).

Purpose: This exercise helps you practice the indexed add() overload for inserting elements at a specific position rather than appending to the end.

Given Input: numbers = {20, 30, 40}, then insert 10 at index 0.

Expected Output: Numbers = [10, 20, 30, 40]

▼ Hint
  • Start by adding a few integers to the list using the regular add() method, which appends to the end.
  • Use the overloaded add(index, element) method to insert at a specific position instead of the end.
  • Passing index 0 shifts every existing element one position to the right to make room.
  • Print the list afterward to confirm the new element is now first.
▼ Solution & Explanation
import java.util.ArrayList;

public class Main {
    public static void main(String[] args) {
        ArrayList<Integer> numbers = new ArrayList<>();
        numbers.add(20);
        numbers.add(30);
        numbers.add(40);

        numbers.add(0, 10);

        System.out.println("Numbers = " + numbers);
    }
}Code language: Java (java)

Explanation:

  • numbers.add(20): Appends elements to the end of the list in the order they are added.
  • numbers.add(0, 10): Uses the two-argument overload of add() to insert 10 at index 0, pushing all other elements one position later.
  • Automatic resizing: The ArrayList internally shifts elements and grows its backing array as needed, so you don't have to manage array indices manually.
  • Alternative: You could rebuild the list with the new element first by creating a new ArrayList and adding elements in the desired order, though the indexed add() is far simpler for a single insertion.

Exercise 4: Retrieve an Element

Problem Statement: Retrieve and print the element at a specific index (e.g., index 3) from an existing ArrayList. Handle cases where the index might be out of bounds.

Purpose: This exercise helps you practice safe element retrieval using try-catch, since accessing an invalid index throws an exception rather than returning null.

Given Input: colors = {"Red", "Green", "Blue"}, retrieve index 3

Expected Output: Index 3 is out of bounds for this list.

▼ Hint
  • Use get(index) to retrieve an element from the list at the specified position.
  • Wrap the retrieval in a try-catch block to handle an invalid index gracefully.
  • Catch IndexOutOfBoundsException, which is the exception ArrayList throws for invalid indices.
  • Print a friendly error message inside the catch block instead of letting the program crash.
▼ Solution & Explanation
import java.util.ArrayList;

public class Main {
    public static void main(String[] args) {
        ArrayList<String> colors = new ArrayList<>();
        colors.add("Red");
        colors.add("Green");
        colors.add("Blue");

        int index = 3;
        try {
            System.out.println("Element at index " + index + " = " + colors.get(index));
        } catch (IndexOutOfBoundsException e) {
            System.out.println("Index " + index + " is out of bounds for this list.");
        }
    }
}Code language: Java (java)

Explanation:

  • colors.get(index): Attempts to retrieve the element at the given position, throwing an exception if the index is invalid.
  • catch (IndexOutOfBoundsException e): Catches the specific exception ArrayList throws when an index is negative or greater than or equal to the list's size.
  • Graceful error handling: Prevents the program from terminating abruptly, instead giving the user a clear explanation of what went wrong.
  • Alternative: You could check index >= 0 && index < colors.size() before calling get(), avoiding the exception entirely, though try-catch is useful when the check itself is easy to forget.

Exercise 5: Update an Element

Problem Statement: Update a specific element in a list of colors (e.g., change "Red" to "Crimson") and display the updated list.

Purpose: This exercise helps you practice the set() method for replacing an element at a known position without removing and re-adding it.

Given Input: colors = {"Red", "Green", "Blue"}, update "Red" to "Crimson"

Expected Output: Updated Colors = [Crimson, Green, Blue]

▼ Hint
  • Locate the index of the element you want to change, either by knowing it in advance or using indexOf().
  • Use the set(index, element) method to replace the element at that position.
  • Unlike add(), set() overwrites the existing element rather than shifting others.
  • Print the list afterward to confirm the update took effect.
▼ Solution & Explanation
import java.util.ArrayList;

public class Main {
    public static void main(String[] args) {
        ArrayList<String> colors = new ArrayList<>();
        colors.add("Red");
        colors.add("Green");
        colors.add("Blue");

        int index = colors.indexOf("Red");
        colors.set(index, "Crimson");

        System.out.println("Updated Colors = " + colors);
    }
}Code language: Java (java)

Explanation:

  • colors.indexOf("Red"): Locates the position of the element to replace without hardcoding an index number.
  • colors.set(index, "Crimson"): Replaces the element at the found index with the new value, leaving the size of the list unchanged.
  • set() versus add(): set() overwrites an existing position, while add(index, element) would instead insert a new element and shift everything else.
  • Alternative: You could loop through the list checking each element with equals() and replace it manually, but set() combined with indexOf() is more direct.

Exercise 6: Remove an Element

Problem Statement: Remove the third element (index 2) from an ArrayList of doubles and print the list to confirm the removal.

Purpose: This exercise helps you practice the indexed remove() method, and understand the difference between removing by index versus by value.

Given Input: values = {1.5, 2.5, 3.5, 4.5}, remove index 2

Expected Output: Values = [1.5, 2.5, 4.5]

▼ Hint
  • Use the remove(int index) overload to remove an element by its position rather than its value.
  • Be careful with Integer wrapper types, since remove(Integer) would instead try to remove a matching value.
  • After removal, all later elements shift one position earlier to fill the gap.
  • Print the list afterward to confirm the correct element was removed.
▼ Solution & Explanation
import java.util.ArrayList;

public class Main {
    public static void main(String[] args) {
        ArrayList<Double> values = new ArrayList<>();
        values.add(1.5);
        values.add(2.5);
        values.add(3.5);
        values.add(4.5);

        values.remove(2);

        System.out.println("Values = " + values);
    }
}Code language: Java (java)

Explanation:

  • values.remove(2): Uses the int overload of remove(), which removes the element at index 2 (the third element) rather than searching for a matching value.
  • Element shifting: After removal, elements that came after index 2 move one position earlier, keeping the list contiguous.
  • int versus Integer overload: remove(int index) removes by position, while remove(Object o) removes by matching value, which is an easy source of bugs with Integer lists specifically.
  • Alternative: You could use values.remove(Double.valueOf(3.5)) to remove by value instead of position, though it requires knowing the exact value in advance.

Exercise 7: Search for an Element

Problem Statement: Search for a user-specified string within an ArrayList. If it exists, return its index; otherwise, print a "Not Found" message.

Purpose: This exercise helps you practice the contains() and indexOf() methods for locating elements within a list.

Given Input: items = {"Pen", "Notebook", "Eraser"}, search for "Notebook"

Expected Output: Found "Notebook" at index 1.

▼ Hint
  • Use contains() to first check whether the target element exists in the list at all.
  • If it exists, use indexOf() to retrieve its position.
  • If contains() returns false, skip the lookup and print a "Not Found" message instead.
  • Remember that both methods rely on equals() to compare elements, which works well for Strings.
▼ Solution & Explanation
import java.util.ArrayList;

public class Main {
    public static void main(String[] args) {
        ArrayList<String> items = new ArrayList<>();
        items.add("Pen");
        items.add("Notebook");
        items.add("Eraser");

        String target = "Notebook";
        if (items.contains(target)) {
            System.out.println("Found \"" + target + "\" at index " + items.indexOf(target) + ".");
        } else {
            System.out.println("Not Found");
        }
    }
}Code language: Java (java)

Explanation:

  • items.contains(target): Checks whether the target string exists anywhere in the list, returning a simple boolean.
  • items.indexOf(target): Returns the position of the first matching element, only called after confirming the element exists.
  • String comparison: Both methods use equals() internally, correctly comparing the contents of Strings rather than their memory references.
  • Alternative: You could skip the contains() check and rely solely on indexOf(), treating a return value of -1 as "not found," which avoids scanning the list twice.

Exercise 8: Check for Empty List

Problem Statement: Create an ArrayList, add a few items, clear the list completely using a built-in method, and verify whether the list is empty.

Purpose: This exercise helps you practice the clear() and isEmpty() methods for resetting and checking a list's state.

Given Input: numbers = {1, 2, 3}, then call clear()

Expected Output:

Before clear: Is Empty = false
After clear: Is Empty = true
▼ Hint
  • Add a few elements to the list first so it starts out non-empty.
  • Check and print the result of isEmpty() before clearing, to establish a baseline.
  • Call clear() to remove all elements from the list at once.
  • Check and print isEmpty() again afterward to confirm the list is now empty.
▼ Solution & Explanation
import java.util.ArrayList;

public class Main {
    public static void main(String[] args) {
        ArrayList<Integer> numbers = new ArrayList<>();
        numbers.add(1);
        numbers.add(2);
        numbers.add(3);

        System.out.println("Before clear: Is Empty = " + numbers.isEmpty());

        numbers.clear();

        System.out.println("After clear: Is Empty = " + numbers.isEmpty());
    }
}Code language: Java (java)

Explanation:

  • numbers.isEmpty(): Returns true only when the list contains zero elements, providing a cleaner check than comparing size() to 0.
  • numbers.clear(): Removes every element from the list in a single call, resetting its size to zero without creating a new list object.
  • Before and after comparison: Demonstrates that clear() actually empties the existing list rather than just reassigning the variable to a new empty list.
  • Alternative: You could reassign numbers = new ArrayList<>() to achieve a similarly empty list, but that creates a new object instead of clearing the existing one, which matters if other references point to the original list.

Exercise 9: Sort Elements

Problem Statement: Write a program to sort a given ArrayList of integers in ascending order, and then in descending order.

Purpose: This exercise helps you practice Collections.sort() and using a custom Comparator for reverse order.

Given Input: numbers = {5, 3, 8, 1, 9}

Expected Output:

Ascending = [1, 3, 5, 8, 9]
Descending = [9, 8, 5, 3, 1]
▼ Hint
  • Use Collections.sort(list) to sort the list in its natural ascending order.
  • Print the list after this first sort to confirm the ascending order.
  • Use Collections.sort(list, Collections.reverseOrder()) to sort the same list in descending order.
  • Print the list again to confirm the order has been reversed.
▼ Solution & Explanation
import java.util.ArrayList;
import java.util.Collections;

public class Main {
    public static void main(String[] args) {
        ArrayList<Integer> numbers = new ArrayList<>();
        numbers.add(5);
        numbers.add(3);
        numbers.add(8);
        numbers.add(1);
        numbers.add(9);

        Collections.sort(numbers);
        System.out.println("Ascending = " + numbers);

        Collections.sort(numbers, Collections.reverseOrder());
        System.out.println("Descending = " + numbers);
    }
}Code language: Java (java)

Explanation:

  • Collections.sort(numbers): Sorts the list in place using the natural ordering of Integer values, which is ascending numerical order.
  • Collections.reverseOrder(): Provides a Comparator that reverses the natural ordering, which Collections.sort() then uses to sort in descending order.
  • In-place sorting: Both calls modify the same list object directly rather than returning a new sorted list.
  • Alternative: You could use numbers.sort(Comparator.reverseOrder()) directly on the list instance instead of passing it through Collections.sort(), since List gained a sort() method in Java 8.

Exercise 10: Copy an ArrayList

Problem Statement: Create an ArrayList of strings, populate it, and copy all its elements into another freshly created ArrayList.

Purpose: This exercise helps you practice creating an independent copy of a list using a copy constructor, avoiding shared references between two lists.

Given Input: original = {"A", "B", "C"}

Expected Output: Copy = [A, B, C]

▼ Hint
  • Create and populate the original ArrayList first with a few elements.
  • Create a second ArrayList by passing the original list into the constructor of the new one.
  • This constructor copies all elements into the new list, rather than making the new list reference the same underlying data.
  • Print the new list to confirm it contains the same elements as the original.
▼ Solution & Explanation
import java.util.ArrayList;

public class Main {
    public static void main(String[] args) {
        ArrayList<String> original = new ArrayList<>();
        original.add("A");
        original.add("B");
        original.add("C");

        ArrayList<String> copy = new ArrayList<>(original);

        System.out.println("Copy = " + copy);
    }
}Code language: Java (java)

Explanation:

  • new ArrayList<>(original): Uses the copy constructor, which creates a new list containing all the same elements as the original at the time of copying.
  • Independent lists: Since the constructor copies element references into a new backing array, modifying copy afterward (like adding or removing elements) does not affect original, and vice versa.
  • Shallow copy note: While the list itself is independent, if the elements were mutable objects rather than immutable Strings, both lists would still reference the same underlying objects.
  • Alternative: You could use copy.addAll(original) on an already-created empty list to achieve the same result, which is useful when the destination list already exists.

Exercise 11: Shuffle a List

Problem Statement: Randomly shuffle the elements in an ArrayList of integers so that they appear in a random order every time the program runs.

Purpose: This exercise helps you practice using Collections.shuffle() to randomize the order of a list in place.

Given Input: numbers = {1, 2, 3, 4, 5}

Expected Output:

Before = [1, 2, 3, 4, 5]
Shuffled = [3, 1, 5, 2, 4]  (order will vary on each run)
▼ Hint
  • Import java.util.Collections to access the shuffle() method.
  • Populate the ArrayList first with the integers in a fixed order.
  • Call Collections.shuffle(list) to randomize the element order in place.
  • Print the list before and after shuffling to observe the change; the exact result will differ each time you run the program.
▼ Solution & Explanation
import java.util.ArrayList;
import java.util.Collections;

public class Main {
    public static void main(String[] args) {
        ArrayList<Integer> numbers = new ArrayList<>();
        numbers.add(1);
        numbers.add(2);
        numbers.add(3);
        numbers.add(4);
        numbers.add(5);

        System.out.println("Before = " + numbers);
        Collections.shuffle(numbers);
        System.out.println("Shuffled = " + numbers);
    }
}Code language: Java (java)

Explanation:

  • Collections.shuffle(numbers): Randomly permutes the elements of the list in place using a default source of randomness.
  • Non-deterministic output: Since shuffle() uses an internal Random instance seeded by the current time by default, the resulting order differs on each program run.
  • In-place modification: The original list object is reordered directly rather than a new shuffled list being created.
  • Alternative: You could pass a seeded Random object, like Collections.shuffle(numbers, new Random(42)), to get a reproducible shuffle order, which is useful for testing.

Exercise 12: Reverse Elements Manually

Problem Statement: Reverse the elements of an ArrayList without using the built-in Collections.reverse() method.

Purpose: This exercise helps you practice the two-pointer swap technique using get() and set(), a pattern also useful outside of lists.

Given Input: numbers = {1, 2, 3, 4, 5}

Expected Output: Reversed = [5, 4, 3, 2, 1]

▼ Hint
  • Use two pointers, one starting at the beginning of the list and one at the end.
  • Swap the elements at these two positions using the set() method.
  • Move the pointers toward the center after each swap.
  • Stop once the pointers meet or cross, since further swapping would just undo the work.
▼ Solution & Explanation
import java.util.ArrayList;

public class Main {
    public static void main(String[] args) {
        ArrayList<Integer> numbers = new ArrayList<>();
        numbers.add(1);
        numbers.add(2);
        numbers.add(3);
        numbers.add(4);
        numbers.add(5);
        int left = 0;
        int right = numbers.size() - 1;
        while (left < right) {
            int temp = numbers.get(left);
            numbers.set(left, numbers.get(right));
            numbers.set(right, temp);
            left++;
            right--;
        }
        System.out.println("Reversed = " + numbers);
    }
}Code language: Java (java)

Explanation:

  • left and right: Two pointers that start at opposite ends of the list and move toward each other.
  • numbers.set(left, numbers.get(right)): Uses get() and set() together to swap the values at the two pointer positions without a built-in swap method.
  • left++ / right--: Advances both pointers toward the middle after each swap, ensuring the loop eventually terminates.
  • Alternative: You could build a brand new ArrayList by iterating through the original from last to first and adding each element, though the two-pointer swap avoids creating extra objects.

Exercise 13: Extract a Sublist

Problem Statement: Extract a portion of an ArrayList (e.g., elements from index 2 to index 6) into a new sublist and print it.

Purpose: This exercise helps you practice the subList() method, and understand its inclusive-start, exclusive-end index convention.

Given Input: numbers = {10, 20, 30, 40, 50, 60, 70, 80}, extract indices 2 through 6

Expected Output: Sublist = [30, 40, 50, 60, 70]

▼ Hint
  • Use the subList(fromIndex, toIndex) method to extract a range of elements from the original list.
  • Remember that fromIndex is inclusive while toIndex is exclusive, so pass one index higher than the last element you want.
  • Wrap the result in a new ArrayList<>(...) constructor to get an independent copy rather than a live view of the original list.
  • Print the sublist to confirm it contains the intended elements.
▼ Solution & Explanation
import java.util.ArrayList;
import java.util.List;

public class Main {
    public static void main(String[] args) {
        ArrayList<Integer> numbers = new ArrayList<>();
        numbers.add(10);
        numbers.add(20);
        numbers.add(30);
        numbers.add(40);
        numbers.add(50);
        numbers.add(60);
        numbers.add(70);
        numbers.add(80);

        List<Integer> sublist = new ArrayList<>(numbers.subList(2, 7));

        System.out.println("Sublist = " + sublist);
    }
}Code language: Java (java)

Explanation:

  • numbers.subList(2, 7): Extracts elements from index 2 up to, but not including, index 7, capturing indices 2 through 6.
  • new ArrayList<>(...): Wraps the returned view in a new list so the sublist is independent, since subList() by itself returns a live view backed by the original list.
  • Live view caveat: Without the copy constructor, structural changes to the original list (like adding or removing elements) could throw a ConcurrentModificationException on the view.
  • Alternative: You could manually loop from index 2 to 6 and add each element to a new ArrayList, which avoids the live-view behavior entirely but requires more code.

Exercise 14: Swap Two Elements

Problem Statement: Write a Java program to swap two elements at specified positions in an ArrayList.

Purpose: This exercise helps you practice using Collections.swap(), a convenient built-in method for exchanging two elements by index.

Given Input: items = {"A", "B", "C", "D"}, swap indices 1 and 3

Expected Output: Swapped = [A, D, C, B]

▼ Hint
  • Use Collections.swap(list, i, j) to swap two elements by their positions in a single call.
  • This built-in method handles the temporary variable logic internally.
  • Make sure both indices are valid positions within the list's current size.
  • Print the list afterward to confirm the two elements traded places.
▼ Solution & Explanation
import java.util.ArrayList;
import java.util.Collections;

public class Main {
    public static void main(String[] args) {
        ArrayList<String> items = new ArrayList<>();
        items.add("A");
        items.add("B");
        items.add("C");
        items.add("D");

        Collections.swap(items, 1, 3);

        System.out.println("Swapped = " + items);
    }
}Code language: Java (java)

Explanation:

  • Collections.swap(items, 1, 3): Swaps the elements currently at index 1 and index 3, handling the exchange internally without needing a manual temporary variable.
  • In-place operation: The same list object is modified directly, with no new list created.
  • Index validity: Both indices must fall within the current bounds of the list, or an IndexOutOfBoundsException will be thrown.
  • Alternative: You could implement the swap manually using get() and set() with a temporary variable, which is exactly what Collections.swap() does internally.

Exercise 15: Join Two Lists

Problem Statement: Create two separate ArrayLists of strings and join/concatenate them into a single, combined ArrayList.

Purpose: This exercise helps you practice the addAll() method for merging the contents of multiple lists into one.

Given Input: listA = {"Apple", "Banana"}, listB = {"Cherry", "Date"}

Expected Output: Combined = [Apple, Banana, Cherry, Date]

▼ Hint
  • Create and populate two separate ArrayLists independently.
  • Create a brand new destination list to hold the combined result.
  • Use the addAll() method twice, once for each source list, to append all their elements into the destination.
  • Print the combined list to confirm all elements are present in order.
▼ Solution & Explanation
import java.util.ArrayList;

public class Main {
    public static void main(String[] args) {
        ArrayList<String> listA = new ArrayList<>();
        listA.add("Apple");
        listA.add("Banana");

        ArrayList<String> listB = new ArrayList<>();
        listB.add("Cherry");
        listB.add("Date");

        ArrayList<String> combined = new ArrayList<>();
        combined.addAll(listA);
        combined.addAll(listB);

        System.out.println("Combined = " + combined);
    }
}Code language: Java (java)

Explanation:

  • combined.addAll(listA): Appends every element from listA to the end of combined, preserving their original order.
  • combined.addAll(listB): Appends every element from listB immediately after listA's elements.
  • New destination list: Using a separate combined list keeps both listA and listB unmodified, unlike calling listA.addAll(listB) directly.
  • Alternative: You could use Stream.concat(listA.stream(), listB.stream()).collect(Collectors.toList()) for a more functional-style approach to merging.

Exercise 16: Clone an ArrayList

Problem Statement: Perform a shallow copy of an ArrayList to another ArrayList using the clone() method.

Purpose: This exercise helps you practice using clone() and understand what "shallow copy" means for a list of objects.

Given Input: original = {"X", "Y", "Z"}

Expected Output: Clone = [X, Y, Z]

▼ Hint
  • Call the clone() method directly on the original ArrayList instance.
  • Since clone() returns a plain Object, cast the result back to the appropriate generic type before using it.
  • Remember that this creates a shallow copy: the new list is a separate object, but if elements were mutable, both lists would still reference the same underlying element objects.
  • Print the cloned list to confirm it contains the same elements as the original.
▼ Solution & Explanation
import java.util.ArrayList;

public class Main {
    public static void main(String[] args) {
        ArrayList<String> original = new ArrayList<>();
        original.add("X");
        original.add("Y");
        original.add("Z");

        @SuppressWarnings("unchecked")
        ArrayList<String> clone = (ArrayList<String>) original.clone();

        System.out.println("Clone = " + clone);
    }
}Code language: Java (java)

Explanation:

  • original.clone(): Creates a shallow copy of the ArrayList, meaning a new list object is created but its elements are not individually duplicated.
  • (ArrayList<String>) original.clone(): Casts the returned Object back to the expected generic type, since clone() has an untyped return signature.
  • @SuppressWarnings("unchecked"): Suppresses the compiler warning that results from this necessary but inherently unchecked cast.
  • Alternative: You could use the copy constructor new ArrayList<>(original) instead of clone(), which is generally preferred in modern Java code since it avoids the unchecked cast entirely.

Exercise 17: Array to ArrayList Conversion

Problem Statement: Convert a standard fixed-size Java array (String[]) into a dynamic ArrayList.

Purpose: This exercise helps you practice bridging arrays and collections using Arrays.asList().

Given Input: String[] array = {"Red", "Green", "Blue"}

Expected Output: List = [Red, Green, Blue]

▼ Hint
  • Use Arrays.asList(array) to wrap the array in a fixed-size List view.
  • Pass that view into the ArrayList constructor to create a fully resizable, independent list.
  • Skipping the ArrayList constructor and using Arrays.asList() alone would limit you to a fixed-size list that doesn't support add() or remove().
  • Print the resulting ArrayList to confirm it contains the same elements as the original array.
▼ Solution & Explanation
import java.util.ArrayList;
import java.util.Arrays;

public class Main {
    public static void main(String[] args) {
        String[] array = {"Red", "Green", "Blue"};
        ArrayList<String> list = new ArrayList<>(Arrays.asList(array));

        System.out.println("List = " + list);
    }
}Code language: Java (java)

Explanation:

  • Arrays.asList(array): Wraps the existing array in a List view backed directly by the array, without copying its elements.
  • new ArrayList<>(...): Copies the elements from that fixed-size view into a brand new, fully resizable ArrayList.
  • Fixed-size limitation: Calling add() or remove() directly on the result of Arrays.asList() throws an UnsupportedOperationException, which is why wrapping it in an ArrayList constructor matters.
  • Alternative: You could loop through the array manually and call add() for each element, though Arrays.asList() combined with the constructor is far more concise.

Exercise 18: ArrayList to Array Conversion

Problem Statement: Convert an ArrayList of integers back into a standard wrapper array (Integer[]).

Purpose: This exercise helps you practice the toArray() method for converting a list back into an array of a specific type.

Given Input: numbers = {1, 2, 3, 4}

Expected Output: Array = [1, 2, 3, 4]

▼ Hint
  • Use the toArray() method available on every ArrayList to produce an array of its elements.
  • Pass a correctly typed array as an argument, such as new Integer[0], so the method returns the proper array type instead of a plain Object[].
  • Store the result in a variable of the matching array type, like Integer[].
  • Use Arrays.toString() to print the array's contents in a readable format.
▼ Solution & Explanation
import java.util.ArrayList;
import java.util.Arrays;

public class Main {
    public static void main(String[] args) {
        ArrayList<Integer> numbers = new ArrayList<>();
        numbers.add(1);
        numbers.add(2);
        numbers.add(3);
        numbers.add(4);

        Integer[] array = numbers.toArray(new Integer[0]);

        System.out.println("Array = " + Arrays.toString(array));
    }
}Code language: Java (java)

Explanation:

  • numbers.toArray(new Integer[0]): Converts the list's elements into an Integer[] array, using the provided zero-length array purely to specify the desired return type.
  • Zero-length array argument: If the array passed in is too small, toArray() allocates a new array of the correct size internally, so a zero-length array is an efficient and idiomatic choice.
  • Arrays.toString(array): Provides a readable, comma-separated representation of the array's contents, since arrays don't have a useful default toString() like ArrayList does.
  • Alternative: You could call numbers.toArray() without arguments to get a plain Object[], but that loses type information and requires casting each element when accessed.

Exercise 19: Replace Elements Conditionally

Problem Statement: Given an ArrayList of integers, replace all negative numbers with the value 0.

Purpose: This exercise helps you practice conditionally updating list elements in place using an index-based loop.

Given Input: numbers = {5, -3, 8, -1, 0, -7}

Expected Output: Result = [5, 0, 8, 0, 0, 0]

▼ Hint
  • Loop through the list using an index-based loop so you can update elements at specific positions.
  • Check whether each element is negative using a simple comparison.
  • Use set(index, 0) to replace any negative value with zero, leaving other values untouched.
  • Avoid using a for-each loop for this task, since modifying list contents by index requires knowing the position.
▼ Solution & Explanation
import java.util.ArrayList;

public class Main {
    public static void main(String[] args) {
        ArrayList<Integer> numbers = new ArrayList<>();
        numbers.add(5);
        numbers.add(-3);
        numbers.add(8);
        numbers.add(-1);
        numbers.add(0);
        numbers.add(-7);
        for (int i = 0; i < numbers.size(); i++) {
            if (numbers.get(i) < 0) {
                numbers.set(i, 0);
            }
        }
        System.out.println("Result = " + numbers);
    }
}Code language: Java (java)

Explanation:

  • for (int i = 0; i < numbers.size(); i++): Uses an index-based loop so each element can be checked and replaced at its exact position.
  • numbers.get(i) < 0: Checks whether the current element is negative before deciding to replace it.
  • numbers.set(i, 0): Overwrites only the negative elements in place, leaving zero and positive values unchanged.
  • Alternative: You could use numbers.replaceAll(n -> n < 0 ? 0 : n) with a lambda expression for a more concise, functional-style solution.

Exercise 20: Filter Even Numbers

Problem Statement: Write a method that takes an ArrayList of integers and removes all odd numbers, leaving only even numbers.

Purpose: This exercise helps you practice the removeIf() method, which safely removes elements matching a condition during a single pass.

Given Input: numbers = {1, 2, 3, 4, 5, 6, 7, 8}

Expected Output: Result = [2, 4, 6, 8]

▼ Hint
  • Use the removeIf() method, which accepts a predicate describing which elements to remove.
  • Write a lambda expression that returns true for odd numbers, since those are the elements you want removed.
  • Check for oddness using the modulus operator.
  • Avoid removing elements while manually iterating with a for-each loop, since that throws a ConcurrentModificationException.
▼ Solution & Explanation
import java.util.ArrayList;

public class Main {
    public static void keepEvens(ArrayList<Integer> numbers) {
        numbers.removeIf(n -> n % 2 != 0);
    }

    public static void main(String[] args) {
        ArrayList<Integer> numbers = new ArrayList<>();
        numbers.add(1);
        numbers.add(2);
        numbers.add(3);
        numbers.add(4);
        numbers.add(5);
        numbers.add(6);
        numbers.add(7);
        numbers.add(8);

        keepEvens(numbers);
        System.out.println("Result = " + numbers);
    }
}Code language: Java (java)

Explanation:

  • numbers.removeIf(n -> n % 2 != 0): Removes every element for which the lambda condition evaluates to true, in this case any number with a non-zero remainder when divided by 2.
  • n % 2 != 0: Identifies odd numbers, since even numbers always produce a remainder of 0 when divided by 2.
  • Safe removal during iteration: removeIf() internally handles the iteration and removal process safely, avoiding the ConcurrentModificationException that manual removal during a for-each loop would cause.
  • Alternative: You could build a brand new list containing only the even numbers using a stream, like numbers.stream().filter(n -> n % 2 == 0).collect(Collectors.toList()), which avoids mutating the original list.

Exercise 21: Trim Capacity

Problem Statement: Optimize the memory of an ArrayList by trimming its capacity to match its current size.

Purpose: This exercise helps you practice using trimToSize(), and understand the difference between a list's size and its internal backing array capacity.

Given Input: ArrayList<Integer> numbers = new ArrayList<>(20); with only 3 elements added

Expected Output: Size = 3

▼ Hint
  • Create the ArrayList with a large initial capacity using the constructor that accepts an int, such as new ArrayList<>(20).
  • Add only a few elements, leaving most of the reserved capacity unused.
  • Call trimToSize() to shrink the internal backing array down to exactly the current number of elements.
  • Note that size() and the list's contents are unaffected by trimming; only the unused reserved space is released.
▼ Solution & Explanation
import java.util.ArrayList;

public class Main {
    public static void main(String[] args) {
        ArrayList<Integer> numbers = new ArrayList<>(20);
        numbers.add(1);
        numbers.add(2);
        numbers.add(3);

        numbers.trimToSize();

        System.out.println("Size = " + numbers.size());
    }
}Code language: Java (java)

Explanation:

  • new ArrayList<>(20): Creates a list with an initial backing array capacity of 20 elements, even though it starts out empty.
  • numbers.trimToSize(): Resizes the internal backing array down to match the current number of elements, releasing the unused reserved capacity back to the JVM.
  • Invisible via public API: There's no public method to directly observe an ArrayList's capacity, so this optimization matters for memory usage internally even though size() still reports 3 both before and after.
  • Alternative: You could avoid over-allocating capacity in the first place by using the no-argument new ArrayList<>() constructor, which starts with a small default capacity and grows only as needed.

Exercise 22: Compare Two Lists

Problem Statement: Compare two ArrayLists to check if they are identical (contain the same elements in the exact same order).

Purpose: This exercise helps you practice using equals() to compare list contents, and understand that order matters for this comparison.

Given Input: listA = {1, 2, 3}, listB = {1, 2, 3}, listC = {3, 2, 1}

Expected Output:

listA equals listB = true
listA equals listC = false
▼ Hint
  • Use the equals() method directly on one ArrayList, passing the other as the argument.
  • ArrayList's equals() implementation checks both that the lists are the same size and that every element matches at the same position.
  • Two lists with the same elements but in a different order are not considered equal by this method.
  • Print the boolean result of each comparison to confirm the expected outcome.
▼ Solution & Explanation
import java.util.ArrayList;

public class Main {
    public static void main(String[] args) {
        ArrayList<Integer> listA = new ArrayList<>();
        listA.add(1);
        listA.add(2);
        listA.add(3);

        ArrayList<Integer> listB = new ArrayList<>();
        listB.add(1);
        listB.add(2);
        listB.add(3);

        ArrayList<Integer> listC = new ArrayList<>();
        listC.add(3);
        listC.add(2);
        listC.add(1);

        System.out.println("listA equals listB = " + listA.equals(listB));
        System.out.println("listA equals listC = " + listA.equals(listC));
    }
}Code language: Java (java)

Explanation:

  • listA.equals(listB): Returns true because both lists contain the same elements in the same order, which is exactly what ArrayList's equals() checks for.
  • listA.equals(listC): Returns false because, despite containing the same elements, listC has them in a different order.
  • Order-sensitive comparison: Unlike a Set, an ArrayList's equality depends on element order, reflecting its nature as a sequential, indexed collection.
  • Alternative: You could manually loop through both lists comparing elements at each index, but equals() already implements this logic correctly and concisely.

Exercise 23: Remove Duplicates (With Set)

Problem Statement: Remove all duplicate elements from an ArrayList by converting it to a HashSet, then converting it back.

Purpose: This exercise helps you practice using a set-backed conversion to quickly deduplicate a list's elements.

Given Input: numbers = {1, 2, 2, 3, 4, 4, 4, 5}

Expected Output: Unique = [1, 2, 3, 4, 5]

▼ Hint
  • Create a set and pass the original ArrayList into its constructor, which automatically discards duplicate values.
  • Create a new ArrayList and pass the set into its constructor to convert the unique values back into a list.
  • Be aware that a plain HashSet does not preserve insertion order, so the resulting list's order may differ from the original.
  • Print the final list to confirm all duplicates have been removed.
▼ Solution & Explanation
import java.util.ArrayList;
import java.util.LinkedHashSet;
import java.util.Set;

public class Main {
    public static void main(String[] args) {
        ArrayList<Integer> numbers = new ArrayList<>();
        numbers.add(1);
        numbers.add(2);
        numbers.add(2);
        numbers.add(3);
        numbers.add(4);
        numbers.add(4);
        numbers.add(4);
        numbers.add(5);

        Set<Integer> uniqueSet = new LinkedHashSet<>(numbers);
        ArrayList<Integer> unique = new ArrayList<>(uniqueSet);

        System.out.println("Unique = " + unique);
    }
}Code language: Java (java)

Explanation:

  • new LinkedHashSet<>(numbers): Copies the list's elements into a set, automatically discarding duplicates while preserving the original insertion order.
  • new ArrayList<>(uniqueSet): Converts the deduplicated set back into a list so the result supports indexed access and the usual ArrayList methods again.
  • LinkedHashSet versus HashSet: A plain HashSet would also remove duplicates but wouldn't guarantee the original order is preserved, which is why LinkedHashSet is used here.
  • Alternative: You could use a plain HashSet if the resulting order doesn't matter for your use case, which has marginally less overhead than LinkedHashSet.

Exercise 24: Remove Duplicates (Without Set)

Problem Statement: Remove all duplicate elements from an ArrayList without using any other collection class (like Set or another list).

Purpose: This exercise helps you practice in-place deduplication using nested loops and careful index management, without relying on auxiliary collections.

Given Input: numbers = {1, 2, 2, 3, 4, 4, 4, 5}

Expected Output: Unique = [1, 2, 3, 4, 5]

▼ Hint
  • Use two nested loops, both operating directly on the original list rather than creating any new collection.
  • For each element at index i, scan the remaining elements from the end of the list backward, checking for duplicates.
  • When a duplicate is found later in the list, remove it immediately using its index.
  • Scanning backward for removals in the inner loop avoids skipping elements that would otherwise happen due to shifting indices after a removal.
▼ Solution & Explanation
import java.util.ArrayList;

public class Main {
    public static void main(String[] args) {
        ArrayList<Integer> numbers = new ArrayList<>();
        numbers.add(1);
        numbers.add(2);
        numbers.add(2);
        numbers.add(3);
        numbers.add(4);
        numbers.add(4);
        numbers.add(4);
        numbers.add(5);
        for (int i = 0; i < numbers.size(); i++) {
            for (int j = numbers.size() - 1; j > i; j--) {
                if (numbers.get(j).equals(numbers.get(i))) {
                    numbers.remove(j);
                }
            }
        }
        System.out.println("Unique = " + numbers);
    }
}Code language: Java (java)

Explanation:

  • Outer loop (index i): Treats each element in turn as the "reference" value to compare against everything after it.
  • Inner loop (index j, counting down): Scans from the end of the list back toward i + 1, checking for any later duplicate of the reference value.
  • numbers.remove(j): Removes a confirmed duplicate immediately; counting the inner loop downward ensures removing an element doesn't disturb the indices still left to check.
  • Alternative: You could achieve a similar in-place result with a single forward pass that shifts elements manually, but the backward-scanning nested loop is simpler to reason about correctly.

Exercise 25: Find Common Elements

Problem Statement: Given two different ArrayLists, find and display all elements that are common to both lists.

Purpose: This exercise helps you practice using contains() to cross-reference the elements of two separate lists.

Given Input: listA = {1, 2, 3, 4, 5}, listB = {3, 4, 5, 6, 7}

Expected Output: Common = [3, 4, 5]

▼ Hint
  • Create a new ArrayList to hold the elements found in both lists.
  • Loop through the first list, and for each element, check whether it also exists in the second list using contains().
  • If an element exists in both lists, add it to the results list.
  • Print the results list to see which elements were shared between the two originals.
▼ Solution & Explanation
import java.util.ArrayList;

public class Main {
    public static void main(String[] args) {
        ArrayList<Integer> listA = new ArrayList<>();
        listA.add(1);
        listA.add(2);
        listA.add(3);
        listA.add(4);
        listA.add(5);

        ArrayList<Integer> listB = new ArrayList<>();
        listB.add(3);
        listB.add(4);
        listB.add(5);
        listB.add(6);
        listB.add(7);

        ArrayList<Integer> common = new ArrayList<>();
        for (Integer value : listA) {
            if (listB.contains(value)) {
                common.add(value);
            }
        }

        System.out.println("Common = " + common);
    }
}Code language: Java (java)

Explanation:

  • for (Integer value : listA): Iterates through every element of the first list to check it against the second.
  • listB.contains(value): Determines whether the current element from listA also appears somewhere in listB.
  • common.add(value): Collects every element confirmed to exist in both lists into the results list.
  • Alternative: You could use retainAll() on a copy of listA, like new ArrayList<>(listA).retainAll(listB), which achieves the same result with a single built-in method call.

Exercise 26: Frequency Counter

Problem Statement: Count the number of times each unique element appears in an ArrayList and store the results in a Map<Element, Integer>.

Purpose: This exercise helps you practice building a frequency map using getOrDefault(), a common pattern for counting occurrences.

Given Input: items = {"apple", "banana", "apple", "orange", "banana", "apple"}

Expected Output:

apple = 3
banana = 2
orange = 1
▼ Hint
  • Create a Map<String, Integer> to store each unique element alongside its count.
  • Loop through the list, and for each element, use getOrDefault() to retrieve its current count (or 0 if not seen yet).
  • Put the incremented count back into the map for that element.
  • After the loop, iterate over the map's entries to print each element with its final frequency.
▼ Solution & Explanation
import java.util.ArrayList;
import java.util.LinkedHashMap;
import java.util.Map;

public class Main {
    public static void main(String[] args) {
        ArrayList<String> items = new ArrayList<>();
        items.add("apple");
        items.add("banana");
        items.add("apple");
        items.add("orange");
        items.add("banana");
        items.add("apple");

        Map<String, Integer> frequency = new LinkedHashMap<>();
        for (String item : items) {
            frequency.put(item, frequency.getOrDefault(item, 0) + 1);
        }

        for (Map.Entry<String, Integer> entry : frequency.entrySet()) {
            System.out.println(entry.getKey() + " = " + entry.getValue());
        }
    }
}Code language: Java (java)

Explanation:

  • Map<String, Integer> frequency: Associates each unique element with a running count of how many times it has appeared.
  • frequency.getOrDefault(item, 0) + 1: Retrieves the current count for an element, defaulting to zero if it's the first occurrence, then increments it.
  • LinkedHashMap: Preserves the order in which elements were first encountered, so the printed output follows a predictable sequence.
  • Alternative: You could use frequency.merge(item, 1, Integer::sum) instead of getOrDefault() combined with put(), which condenses the increment logic into a single method call.

Exercise 27: Split an ArrayList

Problem Statement: Split a large ArrayList into two smaller ArrayLists based on a condition (e.g., one list for strings shorter than 5 characters, and another for strings 5 characters or longer).

Purpose: This exercise helps you practice classifying and distributing elements into separate lists during a single pass.

Given Input: words = {"cat", "elephant", "dog", "hippopotamus", "ant", "kangaroo"}

Expected Output:

Short = [cat, dog, ant]
Long = [elephant, hippopotamus, kangaroo]
▼ Hint
  • Create two empty ArrayLists, one for each category of elements.
  • Loop through the original list once, checking each element's length against the threshold.
  • Add each element to the appropriate list based on the condition.
  • Print both resulting lists to confirm the elements were split correctly.
▼ Solution & Explanation
import java.util.ArrayList;

public class Main {
    public static void main(String[] args) {
        ArrayList<String> words = new ArrayList<>();
        words.add("cat");
        words.add("elephant");
        words.add("dog");
        words.add("hippopotamus");
        words.add("ant");
        words.add("kangaroo");
        ArrayList<String> shortWords = new ArrayList<>();
        ArrayList<String> longWords = new ArrayList<>();
        for (String word : words) {
            if (word.length() < 5) {
                shortWords.add(word);
            } else {
                longWords.add(word);
            }
        }
        System.out.println("Short = " + shortWords);
        System.out.println("Long = " + longWords);
    }
}Code language: Java (java)

Explanation:

  • word.length() < 5: Determines which category a word belongs to based on its character count.
  • shortWords.add(word) / longWords.add(word): Places each word into the appropriate list without modifying the original words list.
  • Single pass: The original list is only iterated once, with each element classified and placed immediately.
  • Alternative: You could use streams with partitioningBy(), like words.stream().collect(Collectors.partitioningBy(w -> w.length() < 5)), which returns both groups in a single Map<Boolean, List<String>>.

Exercise 28: Merge Sorted Lists

Problem Statement: Given two pre-sorted ArrayLists of integers, merge them into a single, final sorted ArrayList without invoking Collections.sort() at the end.

Purpose: This exercise helps you practice the two-pointer merge technique used in merge sort, taking advantage of the fact that both inputs are already sorted.

Given Input: listA = {1, 3, 5, 7}, listB = {2, 4, 6, 8}

Expected Output: Merged = [1, 2, 3, 4, 5, 6, 7, 8]

▼ Hint
  • Use two index variables to track the current position within each of the two source lists.
  • Compare the current elements from both lists, and add the smaller one to the merged result, advancing only that list's pointer.
  • Once one list is fully consumed, append all of the remaining elements from the other list directly.
  • This approach preserves sorted order without needing to call Collections.sort() at the end.
▼ Solution & Explanation
import java.util.ArrayList;

public class Main {
    public static void main(String[] args) {
        ArrayList<Integer> listA = new ArrayList<>();
        listA.add(1);
        listA.add(3);
        listA.add(5);
        listA.add(7);
        ArrayList<Integer> listB = new ArrayList<>();
        listB.add(2);
        listB.add(4);
        listB.add(6);
        listB.add(8);
        ArrayList<Integer> merged = new ArrayList<>();
        int i = 0;
        int j = 0;
        while (i < listA.size() && j < listB.size()) {
            if (listA.get(i) <= listB.get(j)) {
                merged.add(listA.get(i));
                i++;
            } else {
                merged.add(listB.get(j));
                j++;
            }
        }
        while (i < listA.size()) {
            merged.add(listA.get(i));
            i++;
        }
        while (j < listB.size()) {
            merged.add(listB.get(j));
            j++;
        }
        System.out.println("Merged = " + merged);
    }
}Code language: Java (java)

Explanation:

  • while (i < listA.size() && j < listB.size()): Continues comparing elements from both lists as long as both still have unprocessed elements remaining.
  • listA.get(i) <= listB.get(j): Determines which of the two current elements is smaller, adding it to the merged result and advancing only that list's pointer.
  • Trailing while loops: Once one list runs out, the remaining elements of the other list are already sorted, so they can be appended directly without further comparison.
  • Alternative: You could combine both lists and call Collections.sort() on the result, but that ignores the fact that both inputs are already sorted and does unnecessary extra work.

Exercise 29: Find Continuous Sublist Sum

Problem Statement: Given an ArrayList of positive integers, find a contiguous sublist that adds up to a specific target sum.

Purpose: This exercise helps you practice the sliding window technique for a sum-based problem, taking advantage of the fact that all values are positive.

Given Input: numbers = {1, 2, 3, 7, 5}, target = 12

Expected Output: Sublist Sum Found = [2, 3, 7]

▼ Hint
  • Use a sliding window with two pointers representing the start and end of the current sublist.
  • Keep a running sum of the elements currently within the window.
  • If the running sum exceeds the target, shrink the window from the left by subtracting the leftmost element's value and advancing the start pointer.
  • If the running sum exactly matches the target, capture the current window as your answer.
▼ Solution & Explanation
import java.util.ArrayList;

public class Main {
    public static void main(String[] args) {
        ArrayList<Integer> numbers = new ArrayList<>();
        numbers.add(1);
        numbers.add(2);
        numbers.add(3);
        numbers.add(7);
        numbers.add(5);
        int target = 12;
        int start = 0;
        int sum = 0;
        ArrayList<Integer> result = new ArrayList<>();
        for (int end = 0; end < numbers.size(); end++) {
            sum += numbers.get(end);
            while (sum > target && start <= end) {
                sum -= numbers.get(start);
                start++;
            }
            if (sum == target) {
                result = new ArrayList<>(numbers.subList(start, end + 1));
                break;
            }
        }
        System.out.println("Sublist Sum Found = " + result);
    }
}Code language: Java (java)

Explanation:

  • sum += numbers.get(end): Expands the window by adding the next element to the running sum.
  • while (sum > target && start <= end): Shrinks the window from the left whenever the running sum overshoots the target, since all values are positive and removing elements only decreases the sum.
  • sum == target: Confirms the current window's elements add exactly to the target, at which point the matching sublist is captured using subList().
  • Alternative: You could use a brute-force approach checking every possible start and end combination, but the sliding window technique runs in linear time and only works correctly here because all numbers are positive.

Exercise 30: Custom Object Sorting

Problem Statement: Create a custom class Student with attributes id, name, and gpa. Create an ArrayList<Student> and sort the students by their gpa in descending order using a custom Comparator.

Purpose: This exercise helps you practice writing a custom Comparator to sort objects that don't have a natural ordering of their own.

Given Input: students = [(1, "Alice", 3.8), (2, "Bob", 3.2), (3, "Charlie", 3.9)]

Expected Output:

Charlie - GPA: 3.9
Alice - GPA: 3.8
Bob - GPA: 3.2
▼ Hint
  • Define a simple Student class with private fields for id, name, and gpa, plus a constructor and getter methods.
  • Create an ArrayList<Student> and populate it with a few Student objects.
  • Use Collections.sort() with a Comparator that compares two students' gpa values, reversing the natural order to sort from highest to lowest.
  • Print each student's name and gpa after sorting to confirm the descending order.
▼ Solution & Explanation
import java.util.ArrayList;
import java.util.Collections;
import java.util.Comparator;

class Student {
    private int id;
    private String name;
    private double gpa;

    public Student(int id, String name, double gpa) {
        this.id = id;
        this.name = name;
        this.gpa = gpa;
    }

    public String getName() {
        return name;
    }

    public double getGpa() {
        return gpa;
    }
}

public class Main {
    public static void main(String[] args) {
        ArrayList<Student> students = new ArrayList<>();
        students.add(new Student(1, "Alice", 3.8));
        students.add(new Student(2, "Bob", 3.2));
        students.add(new Student(3, "Charlie", 3.9));

        Collections.sort(students, new Comparator<Student>() {
            @Override
            public int compare(Student a, Student b) {
                return Double.compare(b.getGpa(), a.getGpa());
            }
        });

        for (Student student : students) {
            System.out.println(student.getName() + " - GPA: " + student.getGpa());
        }
    }
}Code language: Java (java)

Explanation:

  • Comparator<Student>: Defines custom comparison logic for Student objects, since they don't have a natural ordering of their own.
  • Double.compare(b.getGpa(), a.getGpa()): Compares the two gpa values in reverse order (b before a), which produces a descending sort instead of the default ascending one.
  • Collections.sort(students, comparator): Applies the custom comparator to sort the list in place according to the defined logic.
  • Alternative: You could use a lambda expression instead of an anonymous Comparator class, like students.sort((a, b) -> Double.compare(b.getGpa(), a.getGpa())), or use Comparator.comparingDouble(Student::getGpa).reversed() for a more fluent, readable style.

Filed Under: Java Exercises

Did you find this page helpful? Let others know about it. Sharing helps me continue to create free Python resources.

TweetF  sharein  shareP  Pin

About Vishal

Image

I’m Vishal Hule, the Founder of PYnative.com. As a Python developer, I enjoy assisting students, developers, and learners. Follow me on Twitter.

Related Tutorial Topics:

Java Exercises

All Coding Exercises:

C Exercises
C++ Exercises
Python Exercises
Java Exercises
C# Exercises

Python Exercises and Quizzes

Free coding exercises and quizzes cover Python basics, data structure, data analytics, and more.

  • 15+ Topic-specific Exercises and Quizzes
  • Each Exercise contains 25+ questions
  • Each Quiz contains 25 MCQ
Exercises
Quizzes

Leave a Reply Cancel reply

your email address will NOT be published. all comments are moderated according to our comment policy.

Use <pre> tag for posting code. E.g. <pre> Your entire code </pre>

In: Java Exercises
TweetF  sharein  shareP  Pin

  Java Exercises

  • All Java Exercises
  • Java Exercise for Beginners
  • Java Loops Exercise
  • Java String Exercise
  • Java ArrayList Exercise
  • Java LinkedList Exercise
  • Java HashMap and TreeMap Exercise
  • Java HashSet and TreeSet Exercise
  • Java OOP Exercise
  • Java Methods Exercise
  • Java Enums Exercise
  • Java Exception Handling Exercise
  • Java File Handling Exercise
  • Java Date and Time Exercise
  • Java Data Structures Exercise
  • Java Sorting and Searching Exercise
  • Java Lambda and Functional Interfaces Exercise
  • Java Regex Exercise
  • Java Random Data Generation Exercise
  • Java Generics Exercise
  • Java Reflection Exercise
  • Java JDBC Exercise

All Coding Exercises

Python Exercises C Exercises C++ Exercises Java Exercises C# Exercises

About PYnative

PYnative.com is for Python lovers. Here, You can get Tutorials, Exercises, and Quizzes to practice and improve your Python skills.

Follow Us

To get New Python Tutorials, Exercises, and Quizzes

  • Twitter
  • Facebook
  • Sitemap

Explore Python

  • Learn Python
  • Python Basics
  • Python Databases
  • Python Exercises
  • Python Quizzes
  • Online Python Code Editor
  • Python Tricks

Coding Exercises

  • C Exercises
  • C++ Exercises
  • Python Exercises
  • Java Exercises
  • C# Exercises

Legal Stuff

  • About Us
  • Contact Us

We use cookies to improve your experience. While using PYnative, you agree to have read and accepted our:

  • Terms Of Use
  • Privacy Policy
  • Cookie Policy

Copyright © 2018–2026 pynative.com

Advertisement
Advertisement