蚂蚁运输

源代码:

#include<cstdio>
#include<algorithm>
using namespace std;
int n,m;
struct Node
{
    int X,Y;
}i[1000001];
bool Check(int T) //每次Check()都想不出来,太弱T_T。
{
    int Max=-1e9,Min=1e9;
    for (int a=1;a<=m;a++)
    {
        if (i[a].Y-i[a].X<=T)
          continue;
        Max=max(Max,i[a].X+i[a].Y-T);
        Min=min(Min,i[a].X+i[a].Y+T);
    }
    if (Max>Min)
      return false;
    Max=-1e9,Min=1e9;
    for (int a=1;a<=m;a++)
    {
        if (i[a].Y-i[a].X<=T)
          continue;
        Max=max(Max,i[a].X-i[a].Y-T);
        Min=min(Min,i[a].X-i[a].Y+T);
    }
    if (Max>Min)
      return false;
    return true;
}
int main() //二分答案还是做得少啊!
{
    int T;
    scanf("%d%d",&n,&T);
    while (T--)
    {
        int t1,t2;
        scanf("%d%d",&t1,&t2);
        if (t1>t2)
          swap(t1,t2);
        if (t1!=t2) //若为0,就可以直接忽略了。
        {
            i[++m].X=t1;
            i[m].Y=t2;
        }
    }
    int Left=0,Right=n,Ans(0);
    while (Left<=Right) //二分答案。
    {
        int Mid=(Left+Right)>>1;
        if (Check(Mid))
        {
            Ans=Mid;
            Right=Mid-1;
        }
        else
          Left=Mid+1;
    }
    printf("%d",Ans);
    return 0;
}

/*
    由题可得,在L<R和X<Y的情况下,二分答案应符合,|L-X|+|R-Y|<=Mid,转化:
        L-X+R-Y<=Mid
        L-X+Y-R<=Mid
        X-L+R-Y<=Mid
        X-L+Y-R<=Mid
    综上:
        (L+R-Mid)<=X+Y<=(L+R+Mid)
        (L-R-Mid)<=X-Y<=(L-R+Mid)
    忽略中间内容,检验不等式即可。
因为负数的关系,满足其一则总不等式满足,但由于不知道是哪个分式满足,故全部枚举。
*/
原文地址:https://www.cnblogs.com/Ackermann/p/6020526.html