
一、二分答案核心思路
二分答案准确来说,应该叫做「二分答案 + 判断」。它专门处理大部分「最大值最小」以及「最小值最大」的问题。如果解空间在从小到大的变化过程中,判断答案的结果出现二段性(即满足条件的区间是连续的),此时我们就可以对解空间进行二分,通过判定函数找出最优解。
二、经典例题实战
2.1 木材加工
题目描述
给定 N 根原木,长度分别为 a[1]...a[N]。现在需要切出 K 段等长的木料,问每段木料的最大长度是多少?
算法原理
假设我们要切的长度为 x,那么对于每一根原木 a[i],能切出的段数为 a[i] / x。总段数 sum(a[i] / x) 必须大于等于 K。 随着 x 增大,能切出的段数单调递减。这是一个典型的单调性问题,适合二分查找。 我们需要找到最大的 x,使得 cut(x) >= K。
代码实现
#include <iostream>
using namespace std;
const int N = 1e5 + 10;
typedef long long LL;
LL a[N], n, k;
// 计算在切割长度为 x 情况下能切几段
LL calc(LL x) {
if (x == 0) return 0; // 防止除零
LL cnt = 0;
for (int i = 1; i <= n; i++) {
cnt += a[i] / x;
}
return cnt;
}
int main() {
cin >> n >> k;
for (int i = 1; i <= n; i++) cin >> a[i];
// 二分边界:左边界为 0,右边界设为最大可能长度
l = , r = ;
(l < r) {
LL mid = (l + r + ) / ;
((mid) >= k) {
l = mid;
} {
r = mid - ;
}
}
cout << l << endl;
;
}


