Binary TreesBinary Trees36

  1. 1Preorder Traversal of a Binary Tree using Recursion
  2. 2Preorder Traversal of a Binary Tree using Iteration
  3. 3Postorder Traversal of a Binary Tree Using Recursion
  4. 4Postorder Traversal of a Binary Tree using Iteration
  5. 5Level Order Traversal of a Binary Tree using Recursion
  6. 6Level Order Traversal of a Binary Tree using Iteration
  7. 7Reverse Level Order Traversal of a Binary Tree using Iteration
  8. 8Reverse Level Order Traversal of a Binary Tree using Recursion
  9. 9Find Height of a Binary Tree
  10. 10Find Diameter of a Binary Tree
  11. 11Find Mirror of a Binary Tree - Todo
  12. 12Inorder Traversal of a Binary Tree using Recursion
  13. 13Inorder Traversal of a Binary Tree using Iteration
  14. 14Left View of a Binary Tree
  15. 15Right View of a Binary Tree
  16. 16Top View of a Binary Tree
  17. 17Bottom View of a Binary Tree
  18. 18Zigzag Traversal of a Binary Tree
  19. 19Check if a Binary Tree is Balanced
  20. 20Diagonal Traversal of a Binary Tree
  21. 21Boundary Traversal of a Binary Tree
  22. 22Construct a Binary Tree from a String with Bracket Representation
  23. 23Convert a Binary Tree into a Doubly Linked List
  24. 24Convert a Binary Tree into a Sum Tree
  25. 25Find Minimum Swaps Required to Convert a Binary Tree into a BST
  26. 26Check if a Binary Tree is a Sum Tree
  27. 27Check if All Leaf Nodes are at the Same Level in a Binary Tree
  28. 28Lowest Common Ancestor (LCA) in a Binary Tree
  29. 29Solve the Tree Isomorphism Problem
  30. 30Check if a Binary Tree Contains Duplicate Subtrees of Size 2 or More
  31. 31Check if Two Binary Trees are Mirror Images
  32. 32Calculate the Sum of Nodes on the Longest Path from Root to Leaf in a Binary Tree
  33. 33Print All Paths in a Binary Tree with a Given Sum
  34. 34Find the Distance Between Two Nodes in a Binary Tree
  35. 35Find the kth Ancestor of a Node in a Binary Tree
  36. 36Find All Duplicate Subtrees in a Binary Tree

Find All Unique Triplets That Sum to Zero
Optimal Solution using Two Pointers



Problem Statement

Given an array of integers, your task is to find all the unique triplets (a, b, c) in the array such that:

If no such triplets exist, return an empty list.

Examples

Input ArrayOutput TripletsDescription
[-1, 0, 1, 2, -1, -4][[-1, -1, 2], [-1, 0, 1]]Two unique triplets sum up to 0
[0, 1, 1][]No triplet sums to zero
[0, 0, 0][[0, 0, 0]]Three zeroes sum to zero, one valid triplet
[3, -2, 1, 0][[-2, -1, 3]]Triplet [-2, -1, 3] gives zero
[1, -1][]Only two elements, not enough for a triplet
[][]Empty input, return empty list
[-2, 0, 1, 1, 2][[-2, 0, 2], [-2, 1, 1]]Two triplets, handles duplicates correctly

Solution

The Three Sum problem asks us to find all unique triplets in an array that sum to zero. Since checking all combinations would be too slow for large arrays, we use a more efficient approach by combining sorting with the two-pointer technique.

Understanding the Problem

We are looking for three numbers (a, b, c) such that a + b + c = 0. Importantly, we must not return duplicate triplets. This means if two triplets contain the same numbers in the same order, we should only return one of them.

How We Solve It

First, we sort the input array. This helps us identify and skip duplicates easily and apply the two-pointer strategy efficiently.

We fix one number at a time using a loop (let's call it i) and then look for the other two numbers using two pointers: left starting from i + 1 and right starting from the end of the array.

Depending on the total sum of arr[i] + arr[left] + arr[right], we have three scenarios:

  • If the sum is 0: It's a valid triplet. We add it to the result and skip any duplicate values to avoid repeating the same triplet.
  • If the sum is less than 0: It means the numbers are too small. We move the left pointer to the right to increase the sum.
  • If the sum is greater than 0: It means the numbers are too large. We move the right pointer to the left to reduce the sum.

Handling Edge Cases

  • If the array has less than three elements, it's impossible to form a triplet—return an empty list.
  • If all elements are zero and there are at least three of them, then [0, 0, 0] is the only valid triplet.
  • If the array is empty, simply return an empty list.
  • We must be careful not to include duplicate triplets, which is why we skip over elements that are the same as the previous one (for i, left, and right).

This optimal method ensures that the time complexity is O(n²) instead of the brute force O(n³), making it suitable for large inputs.

Algorithm Steps

  1. Given an array arr of integers.
  2. Sort the array in ascending order.
  3. Traverse the array with index i from 0 to n-2:
  4. → If i > 0 and arr[i] == arr[i-1], skip to avoid duplicates.
  5. → Initialize two pointers: left = i + 1 and right = n - 1.
  6. → While left < right:
  7. → → Calculate the sum: arr[i] + arr[left] + arr[right].
  8. → → If sum is zero, add triplet to result and move left and right to skip duplicates.
  9. → → If sum < 0, move left forward.
  10. → → If sum > 0, move right backward.
  11. Return the list of unique triplets.

Code

Python
JavaScript
Java
C++
C
def three_sum(nums):
    nums.sort()
    result = []
    n = len(nums)

    for i in range(n-2):
        if i > 0 and nums[i] == nums[i-1]:
            continue
        left, right = i+1, n-1
        while left < right:
            total = nums[i] + nums[left] + nums[right]
            if total == 0:
                result.append([nums[i], nums[left], nums[right]])
                while left < right and nums[left] == nums[left+1]:
                    left += 1
                while left < right and nums[right] == nums[right-1]:
                    right -= 1
                left += 1
                right -= 1
            elif total < 0:
                left += 1
            else:
                right -= 1
    return result

# Sample Input
arr = [-1, 0, 1, 2, -1, -4]
print("Triplets:", three_sum(arr))

Time Complexity

CaseTime ComplexityExplanation
Best CaseO(n^2)In the best case, the input is small or contains many duplicate values that allow early skips, but the dominant term is still the nested loop structure with two pointers.
Average CaseO(n^2)We sort the array in O(n log n) and then use a loop with a two-pointer technique inside, which takes O(n^2) in total.
Average CaseO(n^2)Even in the worst case with no duplicate skipping and all combinations needing to be checked, the time complexity remains O(n^2) due to the nested traversal using two pointers.

Space Complexity

O(1)

Explanation: The algorithm uses constant extra space apart from the output list. Sorting is done in-place and only a few variables (i, left, right) are used.



Welcome to ProgramGuru

Sign up to start your journey with us

Support ProgramGuru.org

Mention your name, and programguru.org in the message. Your name shall be displayed in the sponsers list.

PayPal

UPI

PhonePe QR

MALLIKARJUNA M