其他分享
首页 > 其他分享> > BUPT 2022 Summer Training #2(2018-2019 ACM-ICPC, Asia Seoul Regional Contest)

BUPT 2022 Summer Training #2(2018-2019 ACM-ICPC, Asia Seoul Regional Contest)

作者:互联网

E-LED

题目大意:已知N个点(vi,li),求一个分段函数使得这些点在这个函数上的误差的最大值最小。

数据范围:1≤N≤300000,0≤vi,li≤1e9;

解题思路:二分贪心。

二分答案后尽量将排序后的数据归到L1,接着再放到L2,不能放了就是答案无效。

这题的坑在于v=0这个点L0一定为0,还有L1≤L2,所以对于可行解还要比较一下前者最小值和后者最大值的关系。

赛后总结:还算简单的二分,没过的原因主要是这题太晚开了,下次可以经常看看榜单有没有突然比较多人过的题目。

代码如下:

#include<bits/stdc++.h>
using namespace std;
long long n;
struct tu{
    long long x,y;
}e[300300];
double l=0,r=10000000009,ans;
bool cmp(tu a,tu b)
{
    return a.x<b.x;
}
int main()
{
    cin>>n;
    for(long long i=1;i<=n;i++)
    {
        scanf("%lld%lld",&e[i].x,&e[i].y);
    }
    sort(e+1,e+1+n,cmp);
    while(l<=r)
    {
        double mid=(l+r)/2.0;
        bool flag=1;
        long long tag=0;
        double min1=-1,max1=-1,pre=0;
        for(long long i=1;i<=n;i++)
        {
            if(e[i].x==0)
            {
                if(e[i].y>mid)
                {
                    flag=0;
                    break;
                }
                else
                continue;
            }
            if(min1<0)
            {
                if(e[i].y>mid)
                {
                    min1=max1=e[i].y;
                }
                else
                continue;
            }
            else
            {
                double pre_max=max1;
                min1=min(min1,(double)e[i].y);
                max1=max(max1,(double)e[i].y);
                if((max1-min1)>mid*2)
                {
                    tag++;
                    if(tag==1)
                    {
                        pre=pre_max-mid;
                    }
                    if(tag==2)
                    {
                        flag=0;
                        break;
                    }
                    max1=min1=e[i].y;
                }
            }
        }
        if(!flag||(pre>min1+mid&&pre!=0))
        {
            l=mid+0.01;
        }
        else
        {
            r=mid-0.01;
            ans=mid;
        }
    }
    printf("%0.1lf",round(ans*10)/10.0);
    return 0;
}

 

标签:pre,Summer,Training,max1,Regional,mid,long,else,min1
来源: https://www.cnblogs.com/hongyubin/p/16479669.html