Quick Sort as Divide and Conquer in DSA C++ - Time & Space Complexity
We want to understand how the time taken by Quick Sort changes as the list size grows.
How does dividing and sorting smaller parts affect the total work?
Analyze the time complexity of the following Quick Sort code.
void quickSort(int arr[], int low, int high) {
if (low < high) {
int pivot = partition(arr, low, high);
quickSort(arr, low, pivot - 1);
quickSort(arr, pivot + 1, high);
}
}
int partition(int arr[], int low, int high) {
int pivot = arr[high];
int i = low - 1;
for (int j = low; j < high; j++) {
if (arr[j] <= pivot) {
i++;
std::swap(arr[i], arr[j]);
}
}
std::swap(arr[i + 1], arr[high]);
return i + 1;
}
This code sorts an array by picking a pivot, dividing the array around it, and sorting each part recursively.
Identify the loops, recursion, array traversals that repeat.
- Primary operation: The partition function loops through the array segment once.
- How many times: Partition is called recursively on smaller parts until the whole array is sorted.
Each partition splits the array into parts, then sorts each part recursively.
| Input Size (n) | Approx. Operations |
|---|---|
| 10 | About 50 to 70 operations |
| 100 | About 700 to 1,000 operations |
| 1000 | About 10,000 to 15,000 operations |
Pattern observation: The operations grow a bit faster than linear but much slower than quadratic, because the array is divided each time.
Time Complexity: O(n log n)
This means the time grows roughly by multiplying the size by its logarithm, which is efficient for sorting.
[X] Wrong: "Quick Sort always takes the same time regardless of input order."
[OK] Correct: If the pivot divides the array unevenly, Quick Sort can take longer, up to quadratic time in the worst case.
Understanding Quick Sort's time complexity helps you explain why it is fast on average and what affects its speed, a key skill in interviews.
"What if we always picked the middle element as pivot instead of the last? How would the time complexity change?"
Practice
Quick Sort algorithm as a divide and conquer method?Solution
Step 1: Understand divide and conquer in Quick Sort
Quick Sort divides the array into parts around a pivot, then sorts each part separately.Step 2: Recognize the sorting and combining process
After dividing, it sorts the parts recursively and combines them by the nature of recursion.Final Answer:
Divide the array into smaller parts, sort them, and combine results -> Option CQuick Check:
Divide and conquer = divide, sort, combine [OK]
- Confusing Quick Sort with Bubble Sort
- Thinking Quick Sort uses extra memory like Merge Sort
- Believing Quick Sort selects smallest element each time
Solution
Step 1: Identify correct parameter types
The partition function takes an array and two indices low and high to work on a subarray.Step 2: Check return type
Partition returns an integer index where the pivot finally sits.Final Answer:
int partition(int arr[], int low, int high); -> Option BQuick Check:
Partition returns int index with arr[], low, high [OK]
- Using void return type for partition
- Passing array as int instead of int[]
- Adding extra parameters like pivot unnecessarily
arr = [4, 7, 2, 9, 1] with low=0 and high=4 if pivot is chosen as last element?Solution
Step 1: Choose pivot and start partitioning
Pivot is last element: 1. There are no elements less than 1.Step 2: Rearrange array around pivot
No swaps occur in the loop since all arr[j] > 1 for j = 0 to 3. Then swap arr[0] and arr[4], resulting in [1, 7, 2, 9, 4].Final Answer:
[1, 7, 2, 9, 4] -> Option DQuick Check:
Pivot 1 placed at position 0, all to right > 1 [OK]
- Not moving pivot to correct position
- Swapping elements incorrectly
- Assuming pivot stays at end
int partition(int arr[], int low, int high) {
int pivot = arr[high];
int i = low;
for (int j = low; j < high; j++) {
if (arr[j] < pivot) {
swap(arr[i], arr[j]);
i++;
}
}
swap(arr[i], arr[high]);
return i;
}Solution
Step 1: Check initialization of i
i should start at low - 1 to track last smaller element index before loop.Step 2: Understand loop and swaps
Loop runs j from low to high-1 correctly; swapping arr[i+1] and arr[high] places pivot correctly.Final Answer:
Initialization of i should be low - 1 -> Option AQuick Check:
i = low - 1 needed for correct partition [OK]
- Starting i at low causes wrong swaps
- Loop running to high causes out-of-bound errors
- Changing pivot position unnecessarily
arr = [10, 80, 30, 90, 40, 50, 70], what is the state of the array after the first full Quick Sort partition step choosing the last element as pivot?Solution
Step 1: Identify pivot and partition
Pivot is last element 70. Partition rearranges elements less than 70 to left.Step 2: Rearrange array after partition
Elements less than 70: 10, 30, 40, 50. Elements greater: 80, 90. After partition, pivot 70 placed after smaller elements: [10, 30, 40, 50, 70, 80, 90]Final Answer:
[10, 30, 40, 50, 70, 80, 90] -> Option AQuick Check:
Pivot 70 placed after smaller elements [OK]
- Sorting entire array in first step
- Swapping pivot with wrong element
- Assuming pivot moves to last position
Ready to prove it?
Pass the test and this pattern moves unknown
