⬅ Previous Topic
Sliding Window Technique in DSANext Topic ⮕
Binary Search Technique⬅ Previous Topic
Sliding Window Technique in DSANext Topic ⮕
Binary Search TechniqueTopic Contents
The Two Pointers Technique is used to solve problems on linear data structures (like arrays or linked lists). The idea is to use two indices (pointers) to traverse the structure from different directions or speeds to find a desired condition or optimize a process.
This technique is especially effective when dealing with:
Problem Statement: You are given a sorted array of integers and a target sum. Your task is to check whether there exists a pair of numbers in the array whose sum is equal to the target.
Since the array is sorted, we can avoid using nested loops (which would take O(n²) time) by using the two pointers technique to reduce the time complexity to O(n).
The idea is to place one pointer at the start of the array and the other at the end. We move the pointers inward based on the current sum:
left
pointer to the right to increase the sum.right
pointer to the left to decrease the sum.// Input: sorted array and target sum
left = 0
right = array.length - 1
while (left < right):
sum = array[left] + array[right]
if (sum == target):
return true
else if (sum < target):
left += 1
else:
right -= 1
return false
Input:
array = [1, 2, 3, 4, 6, 8, 11] target = 10
left | right | array[left] | array[right] | sum | Action |
---|---|---|---|---|---|
0 | 6 | 1 | 11 | 12 | Sum > 10 → Decrease right |
0 | 5 | 1 | 8 | 9 | Sum < 10 → Increase left |
1 | 5 | 2 | 8 | 10 | Sum = 10 → Found! |
Result: True (Pair found: 2 and 8)
left = 0
and right = 6
(pointing to 1 and 11).right
left (to 8).left
right (to 2).Two pointers rely on the ability to determine whether to increase or decrease the sum by moving a pointer. That only works when the array is sorted — otherwise, increasing or decreasing a pointer won't have predictable effects on the sum.
The two pointers technique is a simple yet powerful way to avoid nested loops and get a linear time solution. It takes advantage of the sorted property to move intelligently and find the answer efficiently.
Problem: Given an array, reverse its elements in-place (without using any extra array).
The Two Pointers Technique is perfect for this problem because we need to swap elements from both ends of the array until we meet in the middle. We don't need to scan the array multiple times — just once, with two pointers approaching each other from opposite sides.
left
pointer starts at the beginning (index 0).right
pointer starts at the end (last index).left += 1
, right -= 1
.left >= right
.left = 0
right = array.length - 1
while (left < right):
swap(array[left], array[right])
left += 1
right -= 1
array = [10, 20, 30, 40, 50]
Step | Left Pointer | Right Pointer | Swap | Array State |
---|---|---|---|---|
Initial | 0 (10) | 4 (50) | 10 <--> 50 | [50, 20, 30, 40, 10] |
After 1st swap | 1 (20) | 3 (40) | 20 <--> 40 | [50, 40, 30, 20, 10] |
After 2nd swap | 2 (30) | 2 (30) | Stop (left == right) | [50, 40, 30, 20, 10] |
[50, 40, 30, 20, 10]
This is a classic example where the Two Pointers Technique simplifies the problem:
Problem: Given a sorted array, remove the duplicates in-place so that each element appears only once and return the new length of the array. The relative order of the elements should be kept the same, and you should not use extra space (O(1) space).
This is a classic case for the Two Pointers Technique. The idea is simple but very efficient:
i
) to keep track of the last unique element (also called the "slow" pointer).j
) to scan the array for the next unique element (also called the "fast" pointer).Since the array is already sorted, duplicates will always be adjacent. So, we can move the fast pointer and compare each element with the last unique value.
When we find a new unique element, we increment the slow pointer and overwrite the duplicate position with the new unique value.
if array is empty:
return 0
i = 0 // slow pointer
for j from 1 to array.length - 1:
if array[j] != array[i]:
i += 1
array[i] = array[j]
return i + 1
Let's walk through an example:
Input: [10, 10, 20, 20, 30, 40, 40]
j (fast) | i (slow) | array[j] | array[i] | Action | Array State |
---|---|---|---|---|---|
1 | 0 | 10 | 10 | Duplicate → skip | [10, 10, 20, 20, 30, 40, 40] |
2 | 0 | 20 | 10 | New value → i++ → array[1] = 20 | [10, 20, 20, 20, 30, 40, 40] |
3 | 1 | 20 | 20 | Duplicate → skip | [10, 20, 20, 20, 30, 40, 40] |
4 | 1 | 30 | 20 | New value → i++ → array[2] = 30 | [10, 20, 30, 20, 30, 40, 40] |
5 | 2 | 40 | 30 | New value → i++ → array[3] = 40 | [10, 20, 30, 40, 30, 40, 40] |
6 | 3 | 40 | 40 | Duplicate → skip | [10, 20, 30, 40, 30, 40, 40] |
Final value of i: 3
New length: i + 1 = 4
Modified Array: [10, 20, 30, 40]
(first 4 elements)
i
always points to the last unique value found.j
explores the array to find the next non-duplicate value.i
and copy array[j]
to array[i]
.By separating the roles of the two pointers:
This method ensures no duplicate is placed in the first part of the array, and the array is modified in-place with minimal code.
The Two Pointers Technique is a simple yet powerful strategy in DSA. It offers elegant solutions to a variety of problems with linear time complexity. Once you learn to spot scenarios where two pointers can be applied, you'll find your problem-solving speed and accuracy improving significantly.
⬅ Previous Topic
Sliding Window Technique in DSANext Topic ⮕
Binary Search TechniqueYou can support this website with a contribution of your choice.
When making a contribution, mention your name, and programguru.org in the message. Your name shall be displayed in the sponsors list.