680. 剪绳子
主要考查浮点数二分思想
#include <iostream>
using namespace std;
const int N = 100010;
int n, m;
int w[N];
bool check(double mid)
{
int cnt = 0;
//(w[i] / mid) 表示每段绳子可以裁剪mid长度的段数
for(int i = 0; i < n; i++){
cnt += (w[i] / mid);
}
return cnt >= m;
}
int main()
{
cin >> n >> m;
for(int i = 0; i < n; i++) cin >> w[i];
double l = 0, r = 1e9;
while(r - l > 1e-4)
{
double mid = (l + r) / 2;
if(check(mid)) l = mid; //如果mid可以裁剪出来 那么最长的长度肯定在右半段->[mid, r]
else r = mid; //否则在左半段 ->[l, mid]
}
printf("%.2f\n", r);
return 0;
}
AcWing 1227. 分巧克力
主要考察整数二分思想
#include <iostream>
using namespace std;
typedef long long LL;
const int N = 100010;
int h[N], w[N];
int n, m;
bool check(int mid)
{
LL res = 0; //因为当长度为1时 可能会越界 所以采用long long类型
for(int i = 0; i < n; i++){
res += (LL)(h[i] / mid) * (w[i] / mid); //长度和宽度分别可以分多少 进行相乘
if(res >= m) return true; //提前退出 可以减少一些时间
}
return false;
}
int main()
{
cin >> n >> m;
for(int i = 0; i < n; i++) cin >> h[i] >> w[i];
int l = 1, r = 1e5;
while(l < r)
{
int mid = r + l + 1 >> 1; //这儿的写法与下面有关 向上取整
if(check(mid)) l = mid;
else r = mid - 1; //防止进入死循环
}
cout << l << endl;
return 0;
}