0% found this document useful (0 votes)
6 views

Lecture 2 Binary SearchTwo Pointers

Uploaded by

nabaye3390
Copyright
© © All Rights Reserved
Available Formats
Download as PPTX, PDF, TXT or read online on Scribd
0% found this document useful (0 votes)
6 views

Lecture 2 Binary SearchTwo Pointers

Uploaded by

nabaye3390
Copyright
© © All Rights Reserved
Available Formats
Download as PPTX, PDF, TXT or read online on Scribd
You are on page 1/ 41

HEADSTART

Programming and Algorithms


Group

INTRO TO BINARY SEARCH AND


TWO POINTERS METHOD
Binary
Search
Searching

We are trying to find something. It can be anything, an


index, an element, a value, a node or even the answer
itself!

So,

Let’s do some searching !!


Where is
54?
Where is
56?
Intuition for
Binary Search
Binary search is an algorithm to quickly search something
in a monotonous collection.

It is based on the observation that once we compare a


value to the required value, we can determine on
which side of this value does our required value
lie. So, we can skip checking that side for our
value.

So, how do we actually apply this observation ?


Active Region is

Implementation
generally
marked by two
variables, start
and end.
Consider a sorted array containing 54.
You wanna find its position.

We’ll maintain an active region where it can be.


Initially, that’s the whole array.

Compare the middle element (mid) of active region with 54.


If it’s greater than 54, change end to mid.
If it’s less than or equal to 54, change start to mid+1.

Repeat till your active region has only one element


(start==end),
Congratulations! You have found 54 or not.
Pseudocode
low = 0, high = n - 1;
while (low <= high)
{
mid = (low + high) / 2;
if(a[mid]==54){
return mid; Can you guess the
}
if (a[mid] < 54) complexity?
{
low = mid + 1;
}
else{
high = mid;
}
}
return -1;
Complexity Calculation
So, first of all let’s imagine an active region in our array
(At the beginning the entire array would be the active
region ).

Then, we check the middle element of this region. Upon


seeing it, either we would have found what we were
searching for or we can determine on which side of this
region does it lie ? Hence in one step we effectively half
the size of our active region.

So, the number of steps to obtain an active region of


size 1 is about log(n).
How Fast Is It?
Find 37!
Binary Search on Answer
Sometimes, it is easy for us to check our answer and we
can also search it binarily ( ie answers after a value are
all true and before a value are all false or vice versa).

This technique is quite useful and can help solve


questions very quickly.

00000000000000001111111111111
Question Time
Question
Find the smallest integral n such that n²+n>1e18

(Try to do it with binary search)


#include<bits/stdc++.h>
using namespace std;

int main(){
long long n = 1e9 ;
long long l = 0, r = n + 1;
while (l < r){
long long mid = (l + r) / 2; Code for
long long temp = mid * mid + mid;

if (temp <= n){


Finding first 1.
l = mid + 1;
}
else{
r = mid;
}
}
cout << r << endl;
return 0;
}
#include<bits/stdc++.h>
using namespace std;

int main(){
long long n = 1e9 ;
long long l = 0, r = n + 1;
while (l < r){
long long mid = (l + r + 1) / 2;
Code for
long long temp = mid * mid + mid; finding
if (temp <= n){
l = mid; last 0.
}
else{
r = mid - 1;
}
}
cout << l << endl;
return 0;
}
Implementing
Interesting, we can see that whenever, searching
anything in a monotonous collection, our binary search
problem can be either be broken down into largest value
satisfying or smallest value not satisfying

Let’s try a question


https://codeforces.com/contest/1873/problem/E
#include<bits/stdc++.h>
#define ll long long
using namespace std;

int main(){
int t;
cin >> t;
while(t--){
ll n, x;
cin >> n >> x;
ll height[n];

for (int i = 0; i < n; i++){


cin >> height[i];
}

ll l = 0, r = 1e10;
while (l < r){

ll mid = (l + r) / 2;
ll count = 0;

for (int i = 0; i < n; i++){


if (mid > height[i]){
count += mid - height[i];
}
}

if (count <= x){


l = mid + 1;
}
else{
r = mid;
}
}
cout << l - 1 << endl;
}
}
https://cses.fi/problemset/task/1620
#include <bits/stdc++.h>
#define ll long long
using namespace std;

int main(){
ll n, k;
cin >> n >> k;
ll times[n];
for (int i = 0; i < n; i++){
cin >> times[i];
}

ll l = 0, r = 1e18 + 1;
while (l < r){

ll mid = (l + r) / 2;
ll count = 0;
bool chk = 0;

for (int i = 0; i < n; i++){

count += mid / times[i];


if (count > 1000000000){
chk = 1;
break;
}

if (count >= k || chk){


r = mid;
}
else{
l = mid + 1;
}

}
cout << l << endl;
}
Binary Search available in
STL?
Direct Functions available in STL library of C++
so you don’t have to write the implementation.

Lower Bound:
Lower Bound of x returns the index of element
greater than or equal to x in a sorted array or
vector.

Upper Bound:
Upper Bound of x returns the index of element
Example
Consider the array A = [1,2,3,3,4,5,6,8]

Lower Bound of 3 = 2
Upper Bound of 3 = 5

Lower Bound of 9 = 8
Upper Bound of 8 = 8

Lower Bound of 0 = 0
Upper Bound of 0 = 0
Some more Questions

https://codeforces.com/problemset/
problem/474/B
https://codeforces.com/problemset/
problem/1703/F
Two
pointe
r
metho
Introduction
The Two Pointers Method is an important technique that is often used
in competitive programming. It is a broad concept which helps us
deal with a multitude of problems.

As the name suggests, we will be using two pointers to approach the


question in hand. This may be applied whenever:

● Dealing with properties of contiguous subarrays


● Dealing with sorted arrays and searching
● Dealing with specifically two values in a given set
Motivation Problem - !
Given two non-decreasingly sorted arrays A and B of sizes n and m
respectively, merge the two arrays to form a third array C such that it is also
non-decreasingly sorted.

Constraints :
1 ≤ n , m ≤ 5 x 105
-109 ≤ A[i] , B[j] ≤ 109 ∀ 0 ≤ i ≤ n - 1 & 0 ≤ j ≤ m - 1

A = [ 10 , 15 , 231 ]
B = [ 12 , 17 , 211 , 420 ,
2911 ]
} C = [ 10 , 12 , 15 , 17 , 211 , 231 , 420
, 2911 ]
https://codeforces.com/edu/course/2/le
sson/9/1/practice/contest/307092/prob
lem/A
Approach - !
Naive Solution :

Create a new array, consisting of elements from both the


given arrays and sort them. The complexity thus achieved
is O( (n + m) log(n + m) ).

Better Solution :

The main observation is that since both arrays are already sorted, we
need not compare elements of the same array. So we only need
to compare the elements of A with elements of B.
#include<bits/stdc++.h>
using namespace std;

int main(){
int n,m;
cin>>n>>m;
int a1[n],a2[m];
vector<int>ans;
for (int i=0;i<n;i++)
cin>>a1[i];
for (int i=0;i<m;i++)
cin>>a2[i];
int first = 0,second = 0;
while (first < n && second < m)
{
if (a1[first] < a2[second]){
ans.push_back(a1[first]);
first++;
}

Solution - !
else{
ans.push_back(a2[second]);
second++;
}
}
if (first < n)
{
for (int i=first;i<n;i++)
ans.push_back(a1[i]);
}
else if (second < m)
{
for (int i=second;i<m;i++)
ans.push_back(a2[i]);
}
for (int i=0;i<n+m;i++)
cout<<ans[i]<<' ';

return 0;
}
Motivation Problem - !!
Given an array of 𝑛 integers 𝑎[𝑖]. Let's say that the segment of this array
𝑎[𝑙..𝑟] (1≤𝑙≤𝑟≤𝑛) is good if the sum of elements on this segment is at most
𝑠. Your task is to find the length of longest good segment.

Constraints :
1 ≤ n ≤ 105 , 1 ≤ s ≤ 1018
1 ≤ A[i] ≤ 109 ∀ 0 ≤ i ≤ n - 1

A=[2,6,4,3,6,8,9
] }
Ans = 4
https://codeforces.com/edu/course/2/le
sson/9/2/practice/contest/307093/prob
lem/A
Approach - !!
Naive Solution :

Check for all subarrays, using prefix sum optimisation this


boils down to number of subarrays i.e. O(n^2)

Better Solution :

Use two pointers lol


#include<bits/stdc++.h>
using namespace std;
int main(){
int n,s;
cin>>n>>s;
int arr[n];
for (int i=0;i<n;i++)
cin>>arr[i];
int l=0,r=0;
int ans = 0;
int sum = arr[l];
while (l < n && r < n)
{
if (sum <= s){
ans = max(ans,r-l+1);
Solution - !!
r++;
sum+=arr[r];
}
else{
sum-=arr[l];
l++;
}
}
cout<<ans<<"\n";
return 0;
}
Enough motivation, now time for
questions.
Three sum?
You are given an array of n integers, and your task is to find
three values (at distinct positions) whose sum is x.

•1≤n≤5000
•1≤x,ai≤10^9

Input:
4 10
1 2 5 7
Output:
0 1 3
https://cses.fi/problemset/task/1641/
Solution
@pag_iitr
facebook.com/sdspag
discord.gg/egUQEdt3

You might also like