[Algo] 二分答案法
1. 机器人跳跃
// 1. 机器人跳跃
// https://www.nowcoder.com/practice/7037a3d57bbd4336856b8e16a9cafd71
bool complete(int energy, vector<int>& height, int max) {
for (int i = 1; i < height.size(); i++) {
if (height[i] > energy) energy -= height[i] - energy;
else energy += energy - height[i];
if (energy >= max) return true;
if (energy < 0) return false;
}
return true;
}
int minEnergy(vector<int>& height) {
int maxHeight = 0;
for (int h : height) maxHeight = maxHeight >= h ? maxHeight : h;
int l = 0, r = maxHeight, m, ans;
while (l <= r) {
m = (l + r) / 2;
if (complete(m, height, maxHeight)) {
ans = m;
r = m - 1;
} else l = m + 1;
}
return ans;
}
2. 找出第K小的数对距离
// 2. 找出第K小的数对距离
// https://leetcode.cn/problems/find-k-th-smallest-pair-distance/
int distanceNoMoreThan(vector<int>& nums, int k)
{
int sum = 0;
for (int l = 0, r = 0; l < nums.size(); l++)
{
while (r + 1 < nums.size() && nums[r + 1] - nums[l] <= k) r++;
sum += r - l;
}
return sum;
}
int smallestDistancePair(vector<int>& nums, int k) {
sort(nums.begin(), nums.end());
int len = nums.size();
int l = 0, r = nums[len - 1] - nums[0], m, ans;
while (l <= r)
{
m = (l + r) / 2;
if (distanceNoMoreThan(nums, m) < k) l = m + 1;
else { ans = m; r = m - 1; }
}
return ans;
}
3. 计算等位时间
// 3. 计算等位时间
// 给定一个数组arr长度为n,表示n个服务员,每服务一个人的时间
// 给定一个正数m,表示有m个人等位,如果你是刚来的人,请问你需要等多久?
// 假设m远远大于n,比如n <= 10^3, m <= 10^9, 且遵循有空直接上的原则
struct Compare {
bool operator()(const pair<int, int>& a, const pair<int, int>& b) {
return a.first > b.first; // pair.first 越小优先级越高
}
};
int waitingTime1(vector<int> &arr, int m)
{
priority_queue<pair<int, int>, vector<pair<int, int>>, Compare> heap;
// pair.first - 空闲时刻, pair.second - 工作效率
for (int i = 0; i < arr.size(); i++) heap.push(make_pair(0, arr[i]));
for (int i = 0; i < m; i++)
{
pair<int, int> cur = heap.top();
heap.pop();
cur.first += cur.second;
heap.push(cur);
}
return heap.top().first;
}
int f(vector<int> &arr, int time)
{
int ans = 0;
for (int num : arr) ans += time / num + 1;
return ans;
}
int waitingTime2(vector<int> &arr, int m)
{
int min_val = INT32_MAX;
for (int num : arr) min_val = min(min_val, num);
int l = 0, r = m * min_val, mid, ans;
while (l <= r)
{
mid = (l + r) / 2;
if (f(arr, mid) < m + 1) l = mid + 1;
// f - 给定时间内能服务的客人总数(包括开始)
else { ans = mid; r = mid - 1; }
}
return ans;
}
标签:二分,arr,nums,int,energy,height,vector,答案
From: https://www.cnblogs.com/yaoguyuan/p/18637490