#5173. 2026/2/27/LH笔记(二分答案)

2026/2/27/LH笔记(二分答案)

当前没有测试数据。

#include<bits/stdc++.h>
#define int long long
using namespace std;
const int N = 2e5 + 10;
int n, m, l[N], s[N];
//计算出供货商提供的木头满足客人要求的最长木头长度
//什么叫做满足客人要求???  木材的数量>=m
//如果分割的木头长度越长  那得到的木材就越少
//不知道答案是几
//我们可以一个个尝试答案
//1 2 3 4 5 6 7
//我们从小到大尝试答案 假设x是第一个不满足条件的
//那答案就是 x-1
//检查 分割的木头长度是h的时候  满足不满足条件
//二分答案
//答案的范围是1,2,3,4,5,,,,,,1e4
//这道题目是要找 最大的答案 
//假设我们现在去尝试答案为10的时候 满不满足条件
//1.答案为10的时候可行
//2.答案为10的时候不可行  一定尝试更小的答案
//如何去判断一道题目能不能用二分答案????
//看题目的答案 是否具有单调性???
//我们去尝试某一个答案
//这个答案 有两种情况
//可能符合要求,如果符合要求 我们能够很明确 要往哪个范围继续尝试答案
//如果不符合要求 我们也很明确往哪个范围尝试答案
//二分答案需要注意的细节:
//1.需要注意数据范围  二分答案的题目 通常数据范围比较大 需要开ll
//2.一定要注意  要能够想清楚 题目的答案范围是从哪到哪
//3.二分答案的精髓是check函数 要想清楚
bool check(int h){
	int cnt = 0;
	for (int i = 1; i <= n; i++){
		cnt += l[i] / h * s[i];
	}
	return cnt >= m;
}
signed main(){//n=1e6
	cin >> n >> m >> l[1] >> s[1];
	for (int i = 2; i <= n; i++){
		l[i] = ((l[i - 1] * 37011 + 10193) % 10000) + 1;
		s[i] = ((s[i - 1] * 73011 + 24793) % 100) + 1;
	}
    int l=1,r=1e4,ans=0;
    while(l<=r){
        int mid=(l+r)/2;
        if(check(mid)==1) ans=mid,l=mid+1;
        else r=mid-1;
    }
    cout<<ans;
	// for (int i = 1; i <= 1e4 + 1; i++){//从小到大 一个个尝试答案
	// 	if (check(i) == 0){
	// 		cout << i - 1;
	// 		return 0;
	// 	}
	// }
	return 0;
}