Start learning free

LESSON 242 OF 348 · HASH TABLE

Remove Duplicates From Array in Kotlin: O(n) with a HashSet

Practice O(n) Read the full explanation

Given an array of integers, return a new array containing only the unique values.

The resulting array can be in any order.

Example:

Input: [2, 3, 1, 1, 4, 3, -2, 1]
Output: [2, 3, 1, 4, -2]
			

Note:

Your algorithm should run in O(n) time and use O(n) extra space.


STEP 1 OF 3
    Ctrl + Enter to check

    KOTLIN · HASH TABLE

    Remove Duplicates From Array in Kotlin, explained

    Problem overview

    The function removeDuplicates receives an IntArray called nums and returns a new IntArray that holds each value of nums exactly once. The result may be in any order. For [2, 3, 1, 1, 4, 3, -2, 1] the answer holds 2, 3, 1, 4, -2, in some order.

    The statement asks for O(n) time and O(n) extra space.

    Approach: let a set do the work

    A set stores each value at most once, and adding a value that is already in it changes nothing. So if you add every element of the array to a HashSet, what remains afterwards is exactly the list of distinct values. Adding is constant time on average, so the loop is linear.

    The simpler approaches cost more. Comparing every pair is O(n²). Sorting first and then dropping neighbours that repeat is O(n log n). The hash set avoids both, at the price of the extra O(n) space the statement allows.

    The set doesn't remember the order in which values went in, which is fine, because the statement accepts any order.

    Here is the idea on [2, 3, 1, 1, 4, 3, -2, 1]. After 2, 3 and the first 1, the set holds three values. The second 1 is already there, so nothing changes. 4 and -2 are new and go in. The second 3 and the third 1 change nothing. The set ends with five values, and those are the answer.

    Step by step

    1. Create the set. uniqueValues is a val holding a new empty HashSet<Int>. The variable never changes; the set's contents do.
    2. Add every element. A for loop names each element value and calls uniqueValues.add(value). No contains check is needed: add simply does nothing, and returns false, when the value is already present.
    3. Convert and return. The function must return an IntArray, and the set is not one, so toIntArray() copies its elements into a new array.

    The solution in Kotlin

    class Solution {
        fun removeDuplicates(nums: IntArray): IntArray {
            val uniqueValues = HashSet<Int>()
            for (value in nums) {
                uniqueValues.add(value)
            }
            return uniqueValues.toIntArray()
        }
    }
    

    Details worth knowing:

    • toIntArray() is defined on collections of Int, so it works on the HashSet<Int> directly. It produces a new array and leaves the set alone. A Set<Int> is not an IntArray, and Kotlin won't convert one to the other on its own.
    • The returned array is new, so nums is not modified.
    • The elements come out in the order the set iterates them. For small integers that often looks sorted, but nothing guarantees it, so don't depend on it.
    • The loop calls add and ignores its Boolean result. That is fine in Kotlin: a function's result may be discarded.

    Complexity

    Time is O(n): the loop makes n constant-time add calls on average, and toIntArray() copies at most n elements. Space is O(n) for the set and the result array, in the worst case where all values are different.

    Edge cases and common mistakes

    • Empty input. The set stays empty and the function returns an empty array.
    • All values equal. [5, 5, 5] gives an array with the single element 5.
    • Expecting the original order. A HashSet doesn't preserve it. If order mattered, you would need a LinkedHashSet (linkedSetOf), but this lesson doesn't require it.
    • Returning the set. The declared return type is IntArray, so returning the set doesn't compile. Convert it first.
    • Using toSet() or distinct() without understanding them. They solve the same problem in one call, but the lesson builds the set by hand so you see the mechanism.

    Testing

    • [2, 3, 1, 1, 4, 3, -2, 1] returns the five values 2, 3, 1, 4, -2, in any order.
    • [] returns [].
    • [5, 5, 5] returns [5].
    Keep going with KotlinAbout 340 step-by-step lessons, from your first line of code to coding interviews. Free to start.
    Start learning free