Predicate Binary Search
Predicate Binary Search
efficiently by narrowing down the search space. In this lesson, we will use
binary search to find the square root of a perfect square number. We will
break down the process into smaller, digestible parts to help you understand
the intuition behind it.
You are given a perfect square number X, and the goal is to find its square
root.
A brute-force approach would be to start from 1 and check each number until
we find the one whose square equals X. For example:
This brute-force approach has a time complexity of O(X), which can be quite
slow for large values of X.
For example, if X = 25, then the numbers 1, 2, 3, 4, and 5 satisfy the condition
num * num <= X. The largest number satisfying this condition will be the
square root of X.
For example :
}
Applying Binary Search
The idea is to use binary search to find the largest num such that num *
num <= X.
Initial Range:
● lo = 0
● hi = X
We will update lo and hi based on the value of mid during each iteration.
Here’s a detailed walkthrough of the binary search process.
Step 1: Initialize
● lo = 0
● hi = 36
Since mid * mid > X, the square root must lie between lo = 0 and hi = mid - 1
= 17.
As mid = 18, since 18*18 is greater than 36, so all the numbers from 18 to 36,
will have their square greater than 36.
● lo = 0, hi = 17
● mid = (lo + hi) / 2 = (0 + 17) / 2 = 8
● mid * mid = 8 * 8 = 64 > 36
● lo = 0, hi = 7
● mid = (lo + hi) / 2 = (0 + 7) / 2 = 3
● mid * mid = 3 * 3 = 9 <= 36
Since mid * mid <= X, update the answer to 3, and continue the search in the
range lo = mid + 1 = 4 to hi = 7.
● lo = 4, hi = 7
● mid = (lo + hi) / 2 = (4 + 7) / 2 = 5
● mid * mid = 5 * 5 = 25 <= 36
Since mid * mid <= X, update the answer to 5, and continue searching
between lo = mid + 1 = 6 and hi = 7.
● lo = 6, hi = 7
● mid = (lo + hi) / 2 = (6 + 7) / 2 = 6
● mid * mid = 6 * 6 = 36 <= 36
● lo = 7, hi = 7
● mid = (lo + hi) / 2 = 7
● mid * mid = 7 * 7 = 49 > 36
Since mid * mid > X, update hi = mid - 1 = 6.
Final Answer
The last value of answer is 6, which is the correct square root of X = 36.
Code :
if(num*num<=x){
return true;
return false;
int main(){
int ans=-1;
while(lo<=hi){
int mid=(lo+hi)/2;
if(good(mid,x)){
ans=mid;
lo=mid+1;
else{
hi = mid-1;
cout<<ans<<endl;
Time Complexity
The time complexity of binary search is O(log X), which is far more efficient
than the brute-force approach (O(X)). This makes binary search ideal for large
numbers.
Learnings :
Binary search is not specific to arrays. If you are able to find patterns in
monotonic predicate functions, they you can apply binary search on it.
If you are able to find that the function is monotonic, you can apply binary
search on it.
Some times, you don’t apply binary search on answer exactly, you have to
apply on different argument, from which you can get answer.
More problems :
https://leetcode.com/problems/capacity-to-ship-packages-within-d-days/descri
ption/
https://leetcode.com/problems/minimum-number-of-days-to-make-m-bouquets
/description/
https://leetcode.com/problems/sum-of-mutated-array-closest-to-target/descript
ion/