得分显示
添加链接描述
题目要求的是找到最大的一个正实数x
那么x的整数位肯定是a[1](数组从1开始)并且x的范围是[a[1],a[1]+1)(左闭右开)
那就是需要在这个范围里面找了,那就是一个浮点数二分的题了
ac代码如下:
#include<bits/stdc++.h>
using namespace std;
#define int long long
const int N = 1e6+10;
const int mod=998244353;
int n;
int a[N],b[100],c[N];
bool check(double val){
double k=val;//每次都加上val,所以先赋值给另外一个变量
for(int i=1;i<=n;i++){
if(a[i]==(int)(val)){
//如果满足的话就+=k,跳出本次循环
val+=k;
continue;
}
else
if(a[i]<(int)(val)){//如果a[i]<(int)(val)就证明当前的mid有点大了,需要更新右边界,所以返回false
return false;
}
else
return true;
}
return true;
}
void solve(){
//int n;
cin>>n;
double ans=0,num=0;
for(int i=1;i<=n;i++){
cin>>a[i];
//num+=a[i];
}
double l=a[1];
//l是最左边也就是a[1]
double r=a[1]+1-0.000001;
//r是最右边,因为右边取不到所以建议一个小的数
while((r-l)>1e-4){//你需要保证输出结果与答案绝对误差不超过1e-4
double mid=(r+l)/2;
if(check(mid)){//check函数是看是不是满足某种条件
//这个题是判断此时的mid 是不是满足题目的要求
//如果满足的话就证明x的范围是在mid和r之间,就需要更新l(左边界)了
l=mid;
ans=max(ans,mid);//取每次满足条件的最大值
}
else{
//如果不满足的话就需要更新r(右边界)
r=mid;
}
}
cout<<fixed<<setprecision(10)<<ans;
}
signed main(){
ios::sync_with_stdio(0);
cin.tie(0), cout.tie(0);
int T=1;
//cin>>T;
while(T--){
solve();
}
return 0;
}
浮点数二分模板:
while(r-l>1e-8){
double mid=(l+r)/2;
if(check(mid)) r=mid;
else l=mid;
}
//浮点数二分不需要考虑边界情况,所以比整数二分简单点,至于是更新左边界还是右边界就看题目
//可以就先这样写,然后根据更新的,来写check判断语句