# Algorithm: dichotomy

Posted by pikebro2002 on Sun, 24 Oct 2021 19:37:41 +0200

In the process of computer learning, algorithm is also a big head, and it is very important. Whether in academia or industry, it is very popular to have strong coding ability. As a future programmer, the algorithm must not fall behind. To this end, I specially open this column to urge myself to learn algorithms, play algorithm problems frequently, use my brain frequently and summarize frequently.
Topic source: teacher ZYJ OJ question (second week)

# 1, Description of basic dichotomy

• binary search, also known as half search and logarithmic search, is a search algorithm for finding a specific element in an ordered array. The search process starts from the middle element of the array. If the middle element is exactly the element to be found, the search process ends; If a specific element is greater than or less than the intermediate element, it is searched in the half of the array that is greater than or less than the intermediate element, and the comparison starts from the intermediate element as at the beginning. If the array is empty in a step, it means it cannot be found. Each comparison of this search algorithm reduces the search scope by half.
• Complexity analysis: in the worst case, the keyword comparison times are log2(n+1), and the expected time complexity is O(log2n);
• Thinking: I don't quite understand. Can I set L = 0 and H = 10 here? (it doesn't seem very good), so it's to set 11. What's the principle?
• A trick: in the question, you can first judge: is this a bipartite problem of type int or a double problem.

# 2, Topic practice

## 1. Stick splitting (Beginner Level)

We have n sticks. Now cut out M sticks of the same length from these sticks. How long is the longest of these m sticks?

input data
Enter two numbers in the first line. N (1 < = n < = 1000) is the number of sticks, m (1 < = m < = 1000) is the number of sticks of the same length to be cut, and then n positive integers represent the length of the original stick (< = 10000)
output data
Each group outputs a line of results, indicating the longest length of the rope after cutting (two decimal places are reserved)
sample input
4 5
5 6 7 8
sample output
4.00

Analysis: to find the longest length, it is easy to think of dichotomy. The length of the stick is divided. Initialize L = 0 and H = max (stick length). If check (mid) passes, the part with length less than or equal to mid will be removed, and a separate ans will be used to record the current result (ps: setting ans is a small trick of its own. When it is not used before, it will always make boundary errors, and unnecessary trouble can be avoided after use). Just keep looking up, and then jump out if l > H and output the result ANS
code:

```#include<cstdio>
#include<cmath>
#include<cstdlib>
#include<iostream>
int n, m;
int a;
using namespace std;
bool check(double x) { //The check function checks whether it is true. The passed in parameter is double
int cnt = 0;
for (int i = 0; i < n; i++) {
cnt += a[i] / x;
}
if (cnt >= m) {
return true;
}
return false;
}

int main() {
cin >> n >> m;
int lmax = 0;
double ans=1;
for (int i = 0; i < n; i++) {
cin >> a[i];
lmax = max(a[i], lmax);
}
double l = 0, h = lmax + 1; //Here + 1 prevents some boundary values from being unavailable
double mid;
while (h-l>0.0001) { //Conventional method of comparing sizes of floating point numbers
mid = (l + h) / 2;
if (check(mid)) {
ans = mid;
l = mid ; //Here you need to remember!! when updating the upper and lower boundaries, you can directly replace them with mid;
}
else {
h = mid;
}
}
printf("%.2lf", ans); //Use printf to output the specified number of floating-point numbers
}

```

The explanation is detailed in the code. This problem is also an introduction to dichotomy, so I won't repeat it.

## 2. Stone movement (difficult)

Title Description
There is a river. There are some stones in the middle of the river. The number of stones and the distance between two adjacent stones are known. Now you can remove some stones. Ask what is the maximum minimum distance between two adjacent stones after removing up to m stones (the first and last stones cannot be removed).

input data
In the first line, enter two numbers. N (2 < = n < = 1000) is the number of stones, m (0 < = m < = n-2) is the number of removable stones, and then n-1 numbers represent the sequence and the distance D (d < = 1000) between two adjacent stones
output data
Output the maximum value of the minimum distance
sample input
4 1
1 2 3
sample output
3

Analysis: first, select the dichotomy according to the "maximum minimum distance" in the title. The minimum distance between two adjacent stones is the dichotomous object, l = 0, H = max (spacing before treatment), and then let nothing but check(mid) whether it can be achieved by moving stones less than m (because if M is not limited, it can be implemented anyway, such as removing all except the two ends); of course, it is difficult to think about it, and the check function is not easy to implement.
code:

```#include<iostream>
using namespace std;
int n, m;
int a;
int dis;
bool check(int x) {
cout << "coming";
int cnt = 0;//Record the number of stones removed
//Check: make the distance between any two adjacent stones > = x, and then judge whether the number of stones removed is < = M
int i = 0;
for (int j = 1; j < n; j++) {

if (dis[j] - dis[i] < x) {
cnt++;
}
else {
i++;
j++;
}
}
if (cnt > m) return false;
return true;

}
int main() {
cin >> n >> m;
for (int i = 0; i < n-1 ; i++) { //A total of n-1 spacing
cin >> a[i];  //a[i] represents the ith spacing
dis[i+1] = dis[i] + a[i];//dis[i] represents the distance from 0 to I (label, starting from 0)
}
dis[n] = dis[n - 1];//Indispensable
int l = 0, h=dis[n], mid;
int ans=0;
while (l < h) {
mid = (l + h) / 2;
if (check(mid)) {
l = mid+1;
ans = mid;
}
else {
h = mid-1 ;  //It needs to be handled here! I don't know how to judge...
}
}
cout << ans;

}
```

There is a doubt about h. many people initialize with a maximum number, such as 1000000. I don't understand?

## 3. Express package

Title Description
An express company needs to deliver n packages to n places and assign a pre-set route to the postman Xiao K. Xiao K needs to drive and deliver them successively according to the order of the route to the place, and can't miss a place. Xiao K gets the time period that each place can sign for, and also knows the distance from one place in the route to the next. If he reaches a certain place If the local time is earlier than the time period that can be signed, you must stay at this place until it can be signed, but not later than the time period that can be signed. It can be considered that the signing process is completed in an instant.
In order to save fuel, Xiao K hopes that the smaller the maximum speed of the car is, the better. You find a solution for him and find out what the minimum maximum speed of the car is.

input data
The first line is a positive integer n (n < 2) × 104), indicating the number of locations where packages need to be transported.
In line n below, there are three positive integers xi,yi and si in line i+1, indicating that the time period for signing in packages at the ith place is [xi,yi] according to the route order, that is, the earliest is from the departure time xi, the latest is from the departure time yi, the distance from the previous place to the ith place is si, and xi in the route is guaranteed to increase.
It can be considered that s1 is the distance from the departure place to the first place, and the departure time is 0.
output data
It only includes an integer, which is the minimum value of the maximum speed of the vehicle, and the result retains two decimal places.
sample input
3
1 2 2
6 6 2
7 8 4
sample output
2.00
Example description
The first segment reaches the first location at the speed of 1 at time 2, the second segment reaches the second location at the speed of 0.5 at time 6, and the third segment reaches the third location at the speed of 2 at time 8.

Topics: C C++ Algorithm